用Raspberry Pi搭建NAS服務(wù)

為何要自建云服務(wù)或者NAS不是本文的重點(diǎn),這里就不說明了。

本文重點(diǎn)在于提供一種價(jià)格低廉的自建云服務(wù)解決方案,并且易于學(xué)習(xí)和再現(xiàn)。

但是,講述如何使用Linux系統(tǒng)以及一些基礎(chǔ)的命令亦不是本文范圍。

所以,開始閱讀前,請先確認(rèn)

本文的適合對象

  1. 我假設(shè)你有使用過Linux操作系統(tǒng)的經(jīng)驗(yàn);假設(shè)你知道什么是sudo、ls、以及文件系統(tǒng)
  2. 我亦假設(shè)你知道什么是RAID、SSH、http/https服務(wù)
  3. 如果要安裝NextCloud,你還必須了解php、編譯、mysql的相關(guān)知識

寫在前面

自從打算著手自建云服務(wù)以來,一直在考慮實(shí)現(xiàn)方案。

成本是首要考慮的因素。畢竟如果自購硬件成本大于租用CVM,那為什么不去租一臺?其次,如果不考慮成本,也完全可以直接采購現(xiàn)成的解決方案,沒必要自己折騰了。
性能是其次的,畢竟是家用,不會有2位數(shù)的在線人數(shù)。
于是便有了這個(gè)方案。

采購準(zhǔn)備

在開始組建軟件前,你首先得準(zhǔn)備一些必須的硬件。這里有一個(gè)清單可以對照著看。
清單里的設(shè)備并不都是需要新購的,你完全可以利用現(xiàn)有的設(shè)備。

清單

  • 一套 Raspberry Pi 3 Model B+(主板、外殼、電源)(約240元)
  • 一根HDMI鏈接線(約10元)
  • 一張16G或以上的Micro SD卡(約30元)
  • Micro SD卡讀卡器
  • 一臺支持HDMI的顯示器
  • USB鼠標(biāo)
  • 一臺用于遠(yuǎn)程連接Raspberry Pi的電腦,或者USB鍵盤
  • 一個(gè)雙盤位硬盤盒
  • 兩塊相同容量的硬盤
  • 建議使用有線網(wǎng)線連接網(wǎng)絡(luò)(約10元)

Raspberry Pi

Raspberry Pi是一款使用ARM芯片的單片機(jī),3B+是他們現(xiàn)在最新的型號。

這是一臺完整的電腦,功能非常強(qiáng)大。3B+使用一款1.4GH的4核64位ARM CPU,1G內(nèi)存,4個(gè)USB 2.0接口,一個(gè)HDMI顯示接口,以及GPIO接口。

更重要的是,其功耗不到15瓦,售價(jià)約只有240元左右,作為一般家用的云服務(wù)主機(jī)簡直完美。

如果你想要更多信息,點(diǎn)擊這里訪問他們的官網(wǎng)

如果你只相信官方指定經(jīng)銷商,這里是一個(gè)官方列表

外殼看起來不是必須的,但建議一定要買,一個(gè)堅(jiān)固的外殼將給24小時(shí)運(yùn)行的主板提供最基礎(chǔ)的物理防護(hù)。

Micro SD卡

Raspberry Pi不含內(nèi)置硬盤,采用外插SD卡作為存儲。所以如果你沒有用剩下的SD卡,可能就需要購買一張。

官方也提供已經(jīng)預(yù)先錄入NOOBS的卡賣,但是這價(jià)格完全不值得——那其實(shí)就是從官網(wǎng)下載了NOOBS,然后直接復(fù)制到卡里而已。

如果你打算新購一張SD卡,建議買讀寫速度快的——越快越好,畢竟這是整個(gè)系統(tǒng)中速度最慢的組件。

Micro SD卡讀卡器

這當(dāng)然是為了讀寫SD卡準(zhǔn)備的,當(dāng)然你手頭很可能已經(jīng)有很多個(gè)了,又或者你的電腦本來就能直接讀取SD卡。即便新買一個(gè),價(jià)格也便宜到忽略不計(jì)。

顯示器

我相信看到本文的家里至少有一臺顯示器或者帶顯示器的筆記本,如果沒有,好吧,你可以檢查一下自己的電視機(jī)是否支持HDMI,支持的話也能拿來用,不然的話還是去買一臺吧。

USB鍵盤

如果打算之后用NOOBS方式安裝系統(tǒng),并且你有一臺筆記本或電腦用來遠(yuǎn)程連接Raspberry Pi,那么USB鍵盤就不是必須的,否則的話就去準(zhǔn)備一個(gè)。

USB鼠標(biāo)

事實(shí)上USB鼠標(biāo)也不是必須的,前提是你有一個(gè)USB鍵盤。

雙盤位硬盤座/硬盤柜

最后需要一個(gè)2盤位的硬盤盒用來接入大容量硬盤作為主要存儲。
建議2盤位是為了成本考慮,淘寶上看了一圈,4盤位的都在400元以上,雖然用3個(gè)盤組RAID5很誘人(速度優(yōu)于2塊硬盤的RAID1),但這不是必須的,2盤位的性能夠用,也位數(shù)據(jù)提供了堅(jiān)實(shí)的保障。

最終我購買了一款A(yù)casis的DS-P2U3C硬盤盒,這大約是我能找到的性價(jià)比最高的金屬外殼硬盤盒,大約130元。如果你不在乎金屬外殼,還有更便宜的選擇。但請仔細(xì)挑選硬盤盒,不要選用那些不帶外部供電的產(chǎn)品。

值得注意的是,Acasis還有一款雙硬盤自帶陣列的硬盤盒,價(jià)格非常誘人,但這是一筆沒有必要的開銷,而且不便以后擴(kuò)展。我們將以軟件實(shí)現(xiàn)陣列功能。

不得不說的是,硬盤柜是略優(yōu)于硬盤底座的一個(gè)選擇,原因當(dāng)然是硬盤柜的外殼提供了基礎(chǔ)的物理防護(hù)。之所以說略優(yōu),是因?yàn)橛脖P本身是有外殼的,并不像電路板那樣怕粉塵,但是如果你害怕自己的硬盤會受物理沖擊,還是選擇一款硬盤柜的好,當(dāng)然相比底座價(jià)格更貴。

硬盤

最后,硬盤可以使用老設(shè)備上淘汰下來的。我就拆了兩塊2.5寸移動硬盤,它們正好都是500G大小。如果沒有現(xiàn)成的硬盤,你就得去買兩塊,容量大小跟你的錢包商量。從目前市場行情看,3TB的3.5寸硬盤是最具性價(jià)比的。你也可以購買SSD硬盤,要提醒的是,速度超過網(wǎng)絡(luò)或者USB 2.0的硬盤在目前的方案上不會帶來任何性能提升。

[圖片上傳失敗...(image-8beea1-1557927673898)]

[圖片上傳失敗...(image-5a6c11-1557927673898)]

開始安裝

為樹莓派安裝操作系統(tǒng)

你的樹莓派已經(jīng)到手,外殼也組裝完畢,讓我們馬上為它安裝操作系統(tǒng)。

NOOBS或者NOOBS

針對這次的需求,如果你對Linux比較熟悉,可以從官網(wǎng)下載安裝Raspbian Stretch Lite。Lite版提供了最少的預(yù)裝軟件,并且不包含圖形界面;這讓你可以按需只安裝必要的軟件,減少空間浪費(fèi),提升服務(wù)器性能。

但是NOOBS方式安裝起來更方便易懂,這正是本文的目標(biāo)。所以我會提供NOOBS的安裝說明。

制作安裝盤

首先將你的SD卡格式化,注意使用FAT32格式,因?yàn)镻i在啟動時(shí)只能識別FAT32文件系統(tǒng)。

然后從官網(wǎng)下載NOOBS文件,如果你的網(wǎng)絡(luò)受限,也可以使用這個(gè)鏈接:百度網(wǎng)盤 提取碼: yawk
目前版本是3.0.1,這個(gè)鏈接會有效至下一個(gè)版本發(fā)布。

NOOBS下載下來是一個(gè)zip文件,你只需將內(nèi)容全部解壓到你的SD卡,安裝盤這就算準(zhǔn)備好了,沒錯(cuò),絲毫不用懷疑。

安裝系統(tǒng)

將制作好的SD卡插入樹莓派,順便接上鼠標(biāo),還有顯示器,然后開機(jī)。

你面臨的第一個(gè)選擇是安裝哪種系統(tǒng),請選擇Raspbian——官方系統(tǒng)。然后跟著向?qū)б徊讲竭x下去就能完成安裝過程,重新啟動后會進(jìn)入初始化設(shè)置。

設(shè)置界面中只有最后一步值得注意,系統(tǒng)會詢問是否需要更新軟件,如果你能夠接入wifi或者網(wǎng)線,就請更新,否則話就跳過,之后我們還是能通過控制臺更新。

系統(tǒng)設(shè)置

現(xiàn)在我們要為之后的作業(yè)做一些基本設(shè)置,包括打開遠(yuǎn)程SSH連接和系統(tǒng)優(yōu)化。

在開始設(shè)置前,如果你還沒有連上網(wǎng)絡(luò),或之前更新軟件失敗?,F(xiàn)在請立即更新。

打開終端——你能在屏幕最上方的任務(wù)欄上找到它,然后依次輸入以下命令:

sudo apt-get update
sudo apt-get upgrade

update命令更新軟件源索引,upgrade命令將更新所有需要升級的軟件。
過程中請留意控制臺輸出,如果有下載失敗可以多試幾次。

設(shè)置啟動到命令行

更新完畢后我們開始配置系統(tǒng)。
在控制臺輸入這條命令:

sudo raspi-config

然后在出現(xiàn)的界面中選擇:

3 Boot Options

然后在第二級菜單中選擇:

B1 Desktop / CLI

最后選擇:

B1 Console

這條設(shè)置樹莓派每次啟動后直接進(jìn)入命令行,而不是圖形桌面,之后的軟件安裝配置大多只能通過命令行進(jìn)行,所以我們用不上圖形桌面。

開啟SSH登錄

從一級菜單,選擇:

5 Interfacing Options

然后選擇

P2 SSH

打開了SSH后,下次啟動時(shí)我們就能通過SSH遠(yuǎn)程連接樹莓派了。

重新劃分系統(tǒng)內(nèi)存

從一級菜單中選

7 Advanced Options

然后

A3 Memory Split

樹莓派的顯卡是共享系統(tǒng)內(nèi)存,我們因?yàn)闊o需使用圖形界面,所以這里輸入8。只要分配8M給顯卡就足夠了,剩下的都能用于系統(tǒng)運(yùn)行。

必要的設(shè)置到此完畢,記得重啟生效。

組建磁盤陣列

對于需要長時(shí)間運(yùn)行的服務(wù),組建RAID1陣列我認(rèn)為是必須的。要注意消費(fèi)級硬盤的可靠性測試都不是基于24小時(shí)運(yùn)行而設(shè)計(jì)的,即便購買了企業(yè)級硬盤,也沒有廠商敢保證他們的硬盤可以抗打雷抗停電——事實(shí)上即便是企業(yè)內(nèi)部服務(wù)器購買了企業(yè)級硬盤,仍然會組建磁盤陣列來保持?jǐn)?shù)據(jù)的安全。說到底,這取決于硬盤里的數(shù)據(jù)對你到底有多重要。

安裝mdadm

警告
組建RAID1過程中,會將兩塊硬盤都格式化。所以在開始前,請確保兩塊硬盤中沒有任何有用的數(shù)據(jù)。
{: .notice--danger}

遠(yuǎn)程連接到你的樹莓派,執(zhí)行以下命令安裝mdadm:

sudo apt-get install mdadm

小貼士
試試

sudo apt-get install mdadm -y

這樣就不用回答『您希望繼續(xù)執(zhí)行嗎?』這樣的問題了。
{: .notice--info}

確認(rèn)兩塊硬盤的設(shè)備名稱

執(zhí)行l(wèi)sblk命令確認(rèn)硬盤設(shè)備名稱

$ lsblk
NAME        MAJ:MIN RM   SIZE RO TYPE  MOUNTPOINT
sda           8:0    0 465.8G  0 disk
...
sdb           8:16   0 465.8G  0 disk
...
mmcblk0     179:0    0  29.8G  0 disk
├─mmcblk0p1 179:1    0   1.8G  0 part
├─mmcblk0p2 179:2    0     1K  0 part
├─mmcblk0p5 179:5    0    32M  0 part
├─mmcblk0p6 179:6    0    66M  0 part  /boot
└─mmcblk0p7 179:7    0  27.9G  0 part  /

可以看到例子中存在3塊disk。
其中mmcblk0是Micro SD卡,sda與sdb則是兩塊硬盤。

創(chuàng)建陣列磁盤md0

使用sda與sdb兩塊硬盤創(chuàng)建新的RAID1硬盤md0

sudo mdadm --create /dev/md0 --level=mirror --raid-devices=2 /dev/sda /dev/sdb

--create /dev/md0 表示新建的設(shè)備名稱為/dev/md0
--level=mirror 表示RAID類型為RAID1,即『鏡像』
--raid-devices=2 表示新RAID盤包含兩個(gè)設(shè)備
最后跟上設(shè)備名稱就回車執(zhí)行。

然后控制臺會輸出以下內(nèi)容:

mdadm: Note: this array has metadata at the start and
    may not be suitable as a boot device.  If you plan to
    store '/boot' on this device please ensure that
    your boot-loader understands md/v1.x metadata, or use
    --metadata=0.90
Continue creating array? 

這個(gè)提示的大意是,正要?jiǎng)?chuàng)建的陣列不支持作為啟動分區(qū)使用,確認(rèn)是否繼續(xù);我們當(dāng)然要輸入y,并回車?yán)^續(xù)。

最后如果看到以下信息,就說明md0創(chuàng)建已經(jīng)成功:

mdadm: Defaulting to version 1.2 metadata
mdadm: array /dev/md0 started.

然后確認(rèn)下新建的md0的運(yùn)行狀態(tài):

# pi @ raspberrypi in ~/tmp [11:45:20] C:2
$ sudo mdadm --detail /dev/md0
/dev/md0:
        Version : 1.2
  Creation Time : Thu May  9 15:14:20 2019
     Raid Level : raid1
     Array Size : 488255488 (465.64 GiB 499.97 GB)
  Used Dev Size : 488255488 (465.64 GiB 499.97 GB)
   Raid Devices : 2
  Total Devices : 2
    Persistence : Superblock is persistent

  Intent Bitmap : Internal

    Update Time : Wed May 15 02:04:02 2019
          State : clean
 Active Devices : 2
Working Devices : 2
 Failed Devices : 0
  Spare Devices : 0

           Name : raspberrypi:0  (local to host raspberrypi)
           UUID : 296a305d:809bf8cd:c259df5a:70488bf7
         Events : 15549

    Number   Major   Minor   RaidDevice State
       0       8        0        0      active sync   /dev/sda
       1       8       16        1      active sync   /dev/sdb

沒有異常,很好,創(chuàng)建成功。

最后不要忘記將md0的信息更新到mdadm.cconf文件,這樣每次開機(jī)啟動時(shí)候mdadm都會自動登記md0設(shè)備。

sudo mdadm --detail --scan --verbose >> /etc/mdadm/mdadm.conf

這條命令會掃描系統(tǒng)上所有已經(jīng)創(chuàng)建的RAID設(shè)備,并將其信息輸出成mdadm.conf能夠識別的格式,最終保存到/etc/mdadm/mdadm.conf文件的末尾

mdadm的功能很強(qiáng)大,包括對raid盤的監(jiān)控、擴(kuò)展等等。
想要學(xué)習(xí)其更高級的使用方法的話,可以查看其man資料。

格式化

在這之前先格式化一下,為md0創(chuàng)建文件系統(tǒng):

sudo mkfs.ext4 /dev/md0

掛載

陣列磁盤已經(jīng)就緒,讓我們掛上它,立即開始使用!

先創(chuàng)建想要掛載的位置

sudo mkdir /mnt/data

然后掛載

sudo mount /dev/md0 /mnt/data

這個(gè)例子將md0盤掛到了/mnt/data目錄中,實(shí)際你可以掛載到自己喜歡的位置,例如:~/data,掛載前別忘了先創(chuàng)建該目錄就行。

好吧,現(xiàn)在開始終于可以通過/mnt/data目錄寫我們的RAID盤了。
但是,等下,別急,如果你不想每次重啟機(jī)器都自己手動掛載,那我們還有最后一步,那就是開機(jī)自動掛載。

開機(jī)自動掛載

linux的磁盤掛載信息都記錄在/etc/fstab文件里
使用你拿手的文本編輯器打開它,本文所有例子將使用nano。

sudo nano /etc/fstab

在文件的最后插入一行:

/dev/md0 /mnt/data ext4 defaults 0 0

如果樂意,你可以加上一行「#」開頭的注釋,這有助于你日后回憶。

Tips
nano中按ctrl+o保存,ctrl+x退出。請留意底部的快捷鍵功能提示
{: notice--info}

至此,一臺掛載了RAID1硬盤的服務(wù)器已經(jīng)準(zhǔn)備完畢。
即使不繼續(xù)安裝任何其他軟件,你也已經(jīng)可以將這臺機(jī)器當(dāng)做一臺可靠的重要數(shù)據(jù)備份機(jī)使用??晌覀儺?dāng)然不會滿足于此,對吧?

下一節(jié)開始將為樹莓派逐步安裝配置各類軟件來為我們更好的服務(wù)。

服務(wù) 服務(wù) 服務(wù)!

終于要開始安裝我們的云服務(wù),這才是我們真正的目標(biāo),之前的都是準(zhǔn)備工作。

但是到了云服務(wù)這塊,可選擇的內(nèi)容非常之多。接下來要做的內(nèi)容并不全都是必須的,可以根據(jù)自己的需要選擇性部署。

syncthing

syncthing是一個(gè)非常有意思的軟件,其主要用途是用來在各個(gè)計(jì)算機(jī)設(shè)備間進(jìn)行文件同步。這『計(jì)算機(jī)設(shè)備』包含很多不同的操作系統(tǒng)甚至是cpu架構(gòu)——同樣包括手機(jī)。

但是要注意syncthing目前并沒有ios版本
這意味著你不能通過蘋果手機(jī)與自己的服務(wù)器進(jìn)行同步。
如果你想用蘋果手機(jī)進(jìn)行云同步,那么可以跳過這一節(jié),試試之后的NextCloud。

syncthing的原理是通過類似電驢的p2p協(xié)議進(jìn)行通訊傳輸。這種協(xié)議不需要使用中央服務(wù)器來保存數(shù)據(jù)并負(fù)責(zé)分發(fā),而是由A機(jī)器直接路由到B機(jī)器來進(jìn)行通訊。

synthing并不需要知道需要通訊的機(jī)器都ip地址,它采用中介服務(wù)器方式,登記連上來的機(jī)器的網(wǎng)絡(luò)信息,負(fù)責(zé)為需要通訊的雙法尋找路由握手。所以synthing不需要通訊雙方都具備公網(wǎng)ip,只要他們能聯(lián)通到同一個(gè)網(wǎng)絡(luò),互相之間就能通訊。

當(dāng)然,假設(shè)AB兩臺機(jī)器都沒有公網(wǎng)ip,要讓他們之間能通訊,肯定是需要經(jīng)過至少一臺具備公網(wǎng)ip的機(jī)器的,這種在通訊雙方間作為橋梁性質(zhì)的機(jī)器稱作中介服務(wù)器,發(fā)揮著路由的作用。

所以你在兩臺機(jī)器間同步數(shù)據(jù)的時(shí)候,你的數(shù)據(jù)可能會經(jīng)過1臺或者多臺中介,最終保存到你指定的計(jì)算機(jī)上。

但是不用擔(dān)心數(shù)據(jù)安全的問題,中介服務(wù)器實(shí)際并不知道自己接收到的數(shù)據(jù)將要傳輸?shù)淖罱K目的地是哪里,下一個(gè)接手的可能是目的地,更多可能是另一臺中介。另外syncthing的數(shù)據(jù)在傳輸時(shí)都使用了TLS進(jìn)行加密。

綜上,syncthing是用來作為同步和備份網(wǎng)盤的極好方案。

想要了解syncthing更多,點(diǎn)擊這里訪問syncthing官網(wǎng)。

Raspberry Pi上的安裝

在Raspberry Pi上安裝syncthing的一個(gè)比較簡單的方式是——直接下載。

你可以從官網(wǎng)找到ARM版的安裝包。
如果你的網(wǎng)絡(luò)受到神秘力量的干擾而無法訪問官網(wǎng),可以轉(zhuǎn)為訪問項(xiàng)目組的github release主頁。
這兩個(gè)地方哪里下載都是一樣的。

要注意的是,為了服務(wù)器穩(wěn)定,請下載最新的release版本,而不是rc候選版本。并且能夠在Raspberry Pi上運(yùn)行的是arm版,而不是arm64.

在Raspberry Pi上可以使用wget命令進(jìn)行文件下載:

wget https://github.com/syncthing/syncthing/releases/download/v1.1.3/syncthing-linux-arm-v1.1.3.tar.gz

下載到你喜歡的地方,然后解壓:

tar -xzvf syncthing-linux-arm-v1.1.3.tar.gz

然后直接執(zhí)行syncthing:

syncthing-linux-arm-v1.1.3/syncthing

注意控制臺的輸出信息,待啟動徹底完成后按下鍵盤的Ctrl+C以中指syncthing。

這是因?yàn)閟yncthing第一次啟動默認(rèn)配置的web管理地址只能從本機(jī)(樹莓派)上訪問,而本機(jī)現(xiàn)在只是一個(gè)控制臺。

開啟遠(yuǎn)程訪問

接著找到syncthing的配置文件,我們要修改它能在局域網(wǎng)其他地方也能訪問。
syncthing的配置文件默認(rèn)放在 ~/.config/syncthing目錄下。

使用nano打開配置文件:

nano ~/.config/syncthing/config.xml

找到這段內(nèi)容:

    <gui enabled="true" tls="false" debugging="false">
        <address>127.0.0.1:8384</address>

將127.0.0.1改成0.0.0.0
改完后看起來這樣:

    <gui enabled="true" tls="false" debugging="false">
        <address>0.0.0.0:8384</address>

保存后再次啟動syncthing,啟動成功后你就可以通過https://ip:8384/ 來訪問你的syncthing管理頁面了。
其中ip是Raspberry Pi的ip地址。

你可以通過ifconfig命令來查看:

sudo ifconfig -a

或者從你的路由器管理頁面上找到。

同步文件夾設(shè)置

事實(shí)上syncthing的官方文檔維護(hù)的不錯(cuò),如果你的網(wǎng)絡(luò)不受神秘力量影響,可以直接查看官方文檔進(jìn)行你的同步文件夾設(shè)置。

如果不幸你訪問不了官方文檔,那么還有個(gè)好消息是syncthing的全中文界面異常完整,設(shè)置非常簡單。
強(qiáng)烈建議你先點(diǎn)擊『添加文件夾』按鈕試試。
[圖片上傳失敗...(image-a75aa5-1557927673898)]
[圖片上傳失敗...(image-8639ed-1557927673898)]
[圖片上傳失敗...(image-475aac-1557927673898)]
在高級選項(xiàng)卡里可以設(shè)置文件類型——發(fā)送與接收、僅發(fā)送、僅接收。

這是非常有用的一個(gè)功能,這意味著你不僅可以建同步目錄,也可以建備份目錄。

Android手機(jī)安裝syncthing

如果前面你仔細(xì)看了,當(dāng)然知道syncthing沒有ios版本。

但壞消息不止這一個(gè)——syncthing的安卓下載放在注明的Google Play商店里。這是個(gè)沒有些特殊手段永遠(yuǎn)都到達(dá)不了地方,是嗎?(笑)

如果你有自己的神通,那是時(shí)候顯現(xiàn)了。
如果你沒有神通,我提供一個(gè)百度網(wǎng)盤 提取碼: x4jj。
這個(gè)是由F-Droid編譯并簽名,且保證與開源源碼一致的版本。
連接里當(dāng)然也提供了F-Droid的簽名,請自行驗(yàn)證。

安卓版syncthing的界面與服務(wù)器幾乎一致(請使用網(wǎng)頁管理頁面,原生界面設(shè)置功能比網(wǎng)頁管理頁面少)

手機(jī)上唯一要多做一步的就是添加設(shè)備,把你的Raspberry Pi上的syncthing添加進(jìn)來,它們舊能同步了。

打開Raspberry Pi上的syncthing的管理頁面,點(diǎn)擊顯示設(shè)備ID,會出現(xiàn)一個(gè)二維碼;然后在手機(jī)上用相機(jī)掃一下二維碼,將得到的ID復(fù)制下來;然后在安卓syncthing上點(diǎn)擊添加設(shè)備,將復(fù)制下來的ID粘貼進(jìn)去,就能方便的設(shè)置成功。

然后你就可以在安卓上設(shè)置需要同步的文件夾推送給Raspberry Pi,或者接收Raspberry Pi要推送給安卓的文件夾。

關(guān)于公網(wǎng)IP

接著會介紹一些web服務(wù)的自建方法。這些web服務(wù),如果你想在外網(wǎng)也能隨時(shí)隨地訪問的話,至少需要一個(gè)公網(wǎng)IP,哪怕是動態(tài)的。
如果不幸你跟我一樣處在可以上外網(wǎng)卻沒有公網(wǎng)IP的情況(ISP劫持了DNS,隱藏了真實(shí)的外網(wǎng)IP,并封鎖所有端口),那么也不要太過氣餒,我至少還有兩個(gè)辦法可以讓你穿透出去。

花生殼

花生殼是國內(nèi)的老牌內(nèi)網(wǎng)穿透服務(wù)商了。
官網(wǎng)連接。
現(xiàn)在買花生棒還送每月2G流量的服務(wù)。
我并不是要在這里推銷花生棒或者花生殼。相反,他們的服務(wù)非常不具性價(jià)比。

首先,所謂的花生棒就是一臺裝了內(nèi)網(wǎng)端口映射工具的低性能單片機(jī),而內(nèi)網(wǎng)端口映射實(shí)際上只要裝一個(gè)軟件就行,所以這100來塊錢實(shí)際就是用來買每月1G流量的(它們的免費(fèi)軟件賬號有1G流量)。

其次,每月2G流量是什么概念?用來傳文件不太合適,記記筆記是夠用的。
最危險(xiǎn)的,免費(fèi)賬號只支持80端口,這是什么概念?意思是你的所有連接只能從http進(jìn)出,而不是https,這等于所有數(shù)據(jù)都裸露在通訊路徑上,不僅未授權(quán)的人可以隨便截取,花生殼的員工也只要簡單的把文件保存下來直接就能看。

那還不如百度網(wǎng)盤?這是肯定的。

花生殼的確有https服務(wù),但是,但是,SSL加密證書得買它們的,價(jià)格呢?都夠我去租一臺CVM了。

Sunny

Sunny ngrok
這并不是ngrok的官網(wǎng),而是用ngrok的1.x開源軟件改造后面向國內(nèi)運(yùn)營的網(wǎng)站。10元/月/端口,限速5M帶寬,對于私用是很實(shí)惠的。
要注意的是,一定要選擇使用https協(xié)議,只有這個(gè)才是加密的。

安裝nginx

上節(jié)介紹的syncthing是本文中唯一一個(gè)不需要公網(wǎng)ip的服務(wù)。
說到底,syncthing通過中介服務(wù)器進(jìn)行數(shù)據(jù)交換,而不是基于web服務(wù)。

在接下來的內(nèi)容中要配置的幾乎都是web服務(wù),我打算把它們都架設(shè)在nginx上。

非常幸運(yùn)的是,apt-get源里提供了nginx的安裝包,這意味著你只要執(zhí)行apt-get就能完成安裝:

sudo apt-get install nginx-full -y

然后通過systemctl配置nginx服務(wù)作為系統(tǒng)服務(wù)開機(jī)自啟:

sudo systemctl enable nginx

如果沒有什么出錯(cuò)信息,那么nginx就算裝成功了。

nginx的配置不在本節(jié)內(nèi)講,這是根據(jù)你需要運(yùn)行什么服務(wù)決定如何添加配置,如果不需要安裝任何web服務(wù),nginx都不需要安裝。

NextCloud

官網(wǎng)在這里。
NextCloud算是老牌的開源云盤了,它并不是一個(gè)同步工具,而是類似DropBox的云盤。雖然也支持文件夾自動上傳,但是對比syncthing就弱了太多。

好消息是,NextCloud支持所有手機(jī)端。
[圖片上傳失敗...(image-f399cb-1557927673898)]

安卓版官網(wǎng)直接能夠下載!
點(diǎn)『App Store』下面那個(gè)『...direct AAPK download...』就行。

Raspberry Pi安裝NextCloud服務(wù)器端

壞消息是,NextCloud對于缺少Linux服務(wù)器經(jīng)驗(yàn)的人來說過于復(fù)雜了。

因?yàn)镹extCloud是用PHP開發(fā)的,所以除了nginx,還需要安裝PHP。

然后NextCloud需要使用數(shù)據(jù)庫,好吧,我推薦安裝MySQL。

一步步來。

安裝PHP7.3

更壞的消息是,NextCloud 16.0需要運(yùn)行在PHP 7.1以上,而apt-get官方源的版本是7.0

所以我們只能自己編譯安裝PHP7.3。

好消息是你看到了本文,按照步驟一步步做下去就能成功。

先為編譯安裝一些必要的依賴包:

sudo apt-get install autoconf build-essential curl libtool \
  libssl-dev libcurl4-openssl-dev libxml2-dev libreadline7 \
  libreadline-dev libzip-dev libzip4 nginx openssl \
  pkg-config zlib1g-dev

準(zhǔn)備好編譯輸出目錄:

mkdir -p ~/bin/php7-latest/

官網(wǎng)下載php-7.3.5.tar.gz源碼包:

wget https://www.php.net/distributions/php-7.3.5.tar.gz

解壓:

tar -xzvf php-7.3.5.tar.gz

配置編譯參數(shù):

./configure --prefix=$HOME/bin/php-latest \
    --enable-mysqlnd \
    --with-pdo-mysql \
    --with-pdo-mysql=mysqlnd \
    --enable-bcmath \
    --enable-fpm \
    --with-fpm-user=www-data \
    --with-fpm-group=www-data \
    --enable-mbstring \
    --enable-shmop \
    --enable-sockets \
    --enable-sysvmsg \
    --enable-sysvsem \
    --enable-sysvshm \
    --enable-zip \
    --with-zlib \
    --with-curl \
    --with-pear \
    --with-openssl \
    --enable-pcntl \
    --with-readline \
    --with-gd

注意控制臺輸出,沒有出錯(cuò)信息才算成功。

編譯:

make

注意控制臺輸出,沒有出錯(cuò)信息才算成功。

安裝:

make install

如果一切順利,所有可執(zhí)行文件都會編譯到~/bin/php7-latest/ 目錄下。

然后將php的執(zhí)行目錄加入系統(tǒng)PATH環(huán)境變量。
如果用的是bash,請編輯/.bashrc;如果是zsh,編輯/.zshrc,在文件最后加入這句:

export PATH=$HOME/bin/php-latest/bin:$HOME/bin/php-latest/sbin:$PATH

用source命令使剛才的更改生效:

source ~/.bashrc

或者

source ~/.zshrc

配置php-fpm作為系統(tǒng)服務(wù)。
這一步有很多做法,可以寫initd腳本,也可以寫systemd配置,也可以使用supervisor進(jìn)行管理。
這里提供一個(gè)可以運(yùn)行的initd腳本:

#! /bin/sh

### BEGIN INIT INFO
# Provides:          php-fpm
# Required-Start:    $remote_fs $network
# Required-Stop:     $remote_fs $network
# Default-Start:     2 3 4 5
# Default-Stop:      0 1 6
# Short-Description: starts php-fpm
# Description:       starts the PHP FastCGI Process Manager daemon
### END INIT INFO

prefix=/home/pi/bin/php-latest
exec_prefix=${prefix}

php_fpm_BIN=${exec_prefix}/sbin/php-fpm
php_fpm_CONF=${prefix}/etc/php-fpm.conf
php_fpm_PID=${prefix}/var/run/php-fpm.pid


php_opts="--fpm-config $php_fpm_CONF --pid $php_fpm_PID"


wait_for_pid () {
    try=0

    while test $try -lt 35 ; do

        case "$1" in
            'created')
            if [ -f "$2" ] ; then
                try=''
                break
            fi
            ;;

            'removed')
            if [ ! -f "$2" ] ; then
                try=''
                break
            fi
            ;;
        esac

        echo -n .
        try=`expr $try + 1`
        sleep 1

    done

}

case "$1" in
    start)
        echo -n "Starting php-fpm "

        $php_fpm_BIN --daemonize $php_opts

        if [ "$?" != 0 ] ; then
            echo " failed"
            exit 1
        fi

        wait_for_pid created $php_fpm_PID

        if [ -n "$try" ] ; then
            echo " failed"
            exit 1
        else
            echo " done"
        fi
    ;;

    stop)
        echo -n "Gracefully shutting down php-fpm "

        if [ ! -r $php_fpm_PID ] ; then
            echo "warning, no pid file found - php-fpm is not running ?"
            exit 1
        fi

        kill -QUIT `cat $php_fpm_PID`

        wait_for_pid removed $php_fpm_PID

        if [ -n "$try" ] ; then
            echo " failed. Use force-quit"
            exit 1
        else
            echo " done"
        fi
    ;;

    status)
        if [ ! -r $php_fpm_PID ] ; then
            echo "php-fpm is stopped"
            exit 0
        fi

        PID=`cat $php_fpm_PID`
        if ps -p $PID | grep -q $PID; then
            echo "php-fpm (pid $PID) is running..."
        else
            echo "php-fpm dead but pid file exists"
        fi
    ;;

    force-quit)
        echo -n "Terminating php-fpm "

        if [ ! -r $php_fpm_PID ] ; then
            echo "warning, no pid file found - php-fpm is not running ?"
            exit 1
        fi

        kill -TERM `cat $php_fpm_PID`

        wait_for_pid removed $php_fpm_PID

        if [ -n "$try" ] ; then
            echo " failed"
            exit 1
        else
            echo " done"
        fi
    ;;

    restart)
        $0 stop
        $0 start
    ;;

    reload)

        echo -n "Reload service php-fpm "

        if [ ! -r $php_fpm_PID ] ; then
            echo "warning, no pid file found - php-fpm is not running ?"
            exit 1
        fi

        kill -USR2 `cat $php_fpm_PID`

        echo " done"
    ;;

    configtest)
        $php_fpm_BIN -t
    ;;

    *)
        echo "Usage: $0 {start|stop|force-quit|restart|reload|status|configtest}"
        exit 1
    ;;

esac

將上面這段腳本保存為/etc/init.d/php-fpm這個(gè)文件即可。

接著運(yùn)行:

sudo systemctl enable php-fpm

安裝MySQL

先更新一下源索引,保證安裝到的是最新版:

sudo apt-get update

安裝MySQL Server:

sudo apt-get install mysql-server

開啟服務(wù)

sudo systemctl enable mysql

登入數(shù)據(jù)庫:

mysql -u root -p

修改root用戶密碼以及允許遠(yuǎn)程登入:

use mysql;
GRANT ALL PRIVILEGES ON *.* TO 'root'@'%' IDENTIFIED BY '你的root賬號密碼' WITH GRANT OPTION;
flush privileges;

然后就可以在別的機(jī)器上用圖形化客戶端接入這個(gè)MySQL了。

下載并安裝NextCloud Server

本文使用的是NextCloud Server 16.0.0.0
從官網(wǎng)下載壓縮包并解壓到/var/www/nextcloud 目錄下。

改一下目錄所有者,因?yàn)閚ginx默認(rèn)使用www-data用戶啟動:

sudo chown -R www-data:www-data /var/www/nextcloud/

根據(jù)官方文檔說明,使用occ命令安裝:

$ cd /var/www/nextcloud/
$ sudo -u www-data php occ  maintenance:install --database
"mysql" --database-name "nextcloud"  --database-user "root" --database-pass
"password" --admin-user "admin" --admin-pass "password"
Nextcloud is not installed - only a limited number of commands are available
Nextcloud was successfully installed

注意控制臺輸出,如果發(fā)現(xiàn)自己什么參數(shù)錯(cuò)了的話,建議整個(gè)目錄刪掉重新來一遍。

配置nginx使用php解析nextcloud

終于到這一步。
先刪除nginx的站點(diǎn)默認(rèn)配置:

sudo rm /etc/nginx/sites-enabled/default

然后新建一個(gè)nextcloud文件。
文件名其實(shí)隨便都可以,nginx啟動時(shí)會讀取這個(gè)目錄下的所有文件。
nextcloud配置內(nèi)容如下:

upstream php-handler {
    server 127.0.0.1:9000;
    #server unix:/var/run/php/php7.0-fpm.sock;
}

server {
    listen 80;
    listen [::]:80;
    server_name cloud.example.com;
    # enforce https
    return 301 https://$server_name$request_uri;
}

server {
    listen 443 ssl http2;
    listen [::]:443 ssl http2;
    server_name cloud.example.com;

    # Use Mozilla's guidelines for SSL/TLS settings
    # https://mozilla.github.io/server-side-tls/ssl-config-generator/
    # NOTE: some settings below might be redundant
    ssl_certificate /etc/ssl/nginx/cloud.example.com.crt;
    ssl_certificate_key /etc/ssl/nginx/cloud.example.com.key;

    # Add headers to serve security related headers
    # Before enabling Strict-Transport-Security headers please read into this
    # topic first.
    # add_header Strict-Transport-Security "max-age=15768000; includeSubDomains; preload;";
    #
    # WARNING: Only add the preload option once you read about
    # the consequences in https://hstspreload.org/. This option
    # will add the domain to a hardcoded list that is shipped
    # in all major browsers and getting removed from this list
    # could take several months.
    add_header X-Content-Type-Options nosniff;
    add_header X-XSS-Protection "1; mode=block";
    add_header X-Robots-Tag none;
    add_header X-Download-Options noopen;
    add_header X-Permitted-Cross-Domain-Policies none;
    add_header Referrer-Policy no-referrer;

    # Remove X-Powered-By, which is an information leak
    fastcgi_hide_header X-Powered-By;

    # Path to the root of your installation
    root /var/www/nextcloud/;

    location = /robots.txt {
        allow all;
        log_not_found off;
        access_log off;
    }

    # The following 2 rules are only needed for the user_webfinger app.
    # Uncomment it if you're planning to use this app.
    #rewrite ^/.well-known/host-meta /public.php?service=host-meta last;
    #rewrite ^/.well-known/host-meta.json /public.php?service=host-meta-json last;

    # The following rule is only needed for the Social app.
    # Uncomment it if you're planning to use this app.
    # rewrite ^/.well-known/webfinger /public.php?service=webfinger last;

    location = /.well-known/carddav {
      return 301 $scheme://$host/remote.php/dav;
    }
    location = /.well-known/caldav {
      return 301 $scheme://$host/remote.php/dav;
    }

    # set max upload size
    client_max_body_size 512M;
    fastcgi_buffers 64 4K;

    # Enable gzip but do not remove ETag headers
    gzip on;
    gzip_vary on;
    gzip_comp_level 4;
    gzip_min_length 256;
    gzip_proxied expired no-cache no-store private no_last_modified no_etag auth;
    gzip_types application/atom+xml application/javascript application/json application/ld+json application/manifest+json application/rss+xml application/vnd.geo+json application/vnd.ms-fontobject application/x-font-ttf application/x-web-app-manifest+json application/xhtml+xml application/xml font/opentype image/bmp image/svg+xml image/x-icon text/cache-manifest text/css text/plain text/vcard text/vnd.rim.location.xloc text/vtt text/x-component text/x-cross-domain-policy;

    # Uncomment if your server is build with the ngx_pagespeed module
    # This module is currently not supported.
    #pagespeed off;

    location / {
        rewrite ^ /index.php$request_uri;
    }

    location ~ ^\/(?:build|tests|config|lib|3rdparty|templates|data)\/ {
        deny all;
    }
    location ~ ^\/(?:\.|autotest|occ|issue|indie|db_|console) {
        deny all;
    }

    location ~ ^\/(?:index|remote|public|cron|core\/ajax\/update|status|ocs\/v[12]|updater\/.+|oc[ms]-provider\/.+)\.php(?:$|\/) {
        fastcgi_split_path_info ^(.+?\.php)(\/.*|)$;
        include fastcgi_params;
        fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
        fastcgi_param PATH_INFO $fastcgi_path_info;
        fastcgi_param HTTPS on;
        #Avoid sending the security headers twice
        fastcgi_param modHeadersAvailable true;
        fastcgi_param front_controller_active true;
        fastcgi_pass php-handler;
        fastcgi_intercept_errors on;
        fastcgi_request_buffering off;
    }

    location ~ ^\/(?:updater|oc[ms]-provider)(?:$|\/) {
        try_files $uri/ =404;
        index index.php;
    }

    # Adding the cache control header for js and css files
    # Make sure it is BELOW the PHP block
    location ~ \.(?:css|js|woff2?|svg|gif)$ {
        try_files $uri /index.php$request_uri;
        add_header Cache-Control "public, max-age=15778463";
        # Add headers to serve security related headers (It is intended to
        # have those duplicated to the ones above)
        # Before enabling Strict-Transport-Security headers please read into
        # this topic first.
        # add_header Strict-Transport-Security "max-age=15768000; includeSubDomains; preload;";
        #
        # WARNING: Only add the preload option once you read about
        # the consequences in https://hstspreload.org/. This option
        # will add the domain to a hardcoded list that is shipped
        # in all major browsers and getting removed from this list
        # could take several months.
        add_header X-Content-Type-Options nosniff;
        add_header X-XSS-Protection "1; mode=block";
        add_header X-Robots-Tag none;
        add_header X-Download-Options noopen;
        add_header X-Permitted-Cross-Domain-Policies none;
        add_header Referrer-Policy no-referrer;

        # Optional: Don't log access to assets
        access_log off;
    }

    location ~ \.(?:png|html|ttf|ico|jpg|jpeg)$ {
        try_files $uri /index.php$request_uri;
        # Optional: Don't log access to other assets
        access_log off;
    }
}

這個(gè)配置模板是從官方文檔復(fù)制過來的,連接見本節(jié)最后。
注意將cloud.example.com替換成自己的域名或者ip地址。

    ssl_certificate /etc/ssl/nginx/cloud.example.com.crt;
    ssl_certificate_key /etc/ssl/nginx/cloud.example.com.key;

這兩句指定了SSL證書存放的位置,有證書的話請自行放置并修改。

接著記得重啟下nginx:

sudo systemctl restart nginx

現(xiàn)在你應(yīng)該能從 https://ip 或者域名打開nextcloud的網(wǎng)頁版。
這個(gè)地址也是你的手機(jī)客戶端連接服務(wù)器時(shí)的地址。

更多信息請參考官網(wǎng)文檔,上面還有一個(gè)將nextcloud配置到子路徑下的模板

安裝安卓版nextcloud

這根本不值得寫,只要從官網(wǎng)下載了apk裝上就行。
啟動后選擇自建服務(wù)器,輸入之前部署在Raspberry Pi上的url地址,根據(jù)向?qū)б宦废乱徊骄托小?/p>

至此,自建NextCloud云盤終于煉成。

寫在最后

是時(shí)候來計(jì)算下運(yùn)營成本。
Raspberry Pi的功率為 5V x 2.5A = 12.5W
硬盤底座的功率為 12V x 3A = 36W
總計(jì) 48.5W
每天能耗 48.5W x 24H = 1164WH = 1.164千瓦時(shí)
如果每個(gè)字平均按0.5元算,一天電費(fèi)0.582元,一個(gè)月不到18元。

事實(shí)上實(shí)際使用起來還要低一些,畢竟不是一直滿功率運(yùn)行——事實(shí)上大多時(shí)候可能都是在空轉(zhuǎn)。

開始掌控自己的數(shù)據(jù)吧。
1.png
2.png
3.png
4.png
5.png
6.png
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容