2014年11月27日 星期四

PHP 偵測瀏覽器是否為手機

原理:

使用$_SERVER['HTTP_USER_AGENT']

前言:

忘了從哪邊看到的,HTTP Header的User-Agent是可以更改的,所以最好是在前端判斷(?)。不過我想用php來判斷應該可以應付大部分情況,而且今天都在遮疼php的解決方案,就把他記錄下來。

一、使用get_browser()

http://php.net/get_browser
get_browser()預設不能直接使用,須先做設定
安裝:
1. 到 http://browscap.org/ 下載PHP版本的full_php_browscap.ini
2. 然後設定php.ini 裡面[browscap]的
browscap = /your_browscap_ini_path/full_php_browscap.ini
3. 重啟apache
用法:
$browser = get_browser(null, true);
echo "is mobile:".$browser['ismobiledevice'];
報錯:
PHP:  syntax error, unexpected $end, expecting ']' in /etc/php/conf.d/full_php_browscap.ini on line 78
解法:
$ sed 's/;/\\\;/g' original_browscap.ini > browscap.ini
如果original_browscap.ini放在/etc/php/conf.d/ 下記得把original_browscap.ini移除,不然仍會報錯

因為使用browscap.ini ( 23MB ),刷頁面有呼叫get_browser()時會多800ms(不呼叫沒事),又ini_set無法在script時去設定browscap.ini
http://stackoverflow.com/questions/2545910/php-using-browscap-ini-on-shared-host-ini-set-failing
'browscap' is changeable only in the system php.ini and/or httpd.conf. You cannot set it at the script level.
且在cli時如果不加 -n 也會延遲,所以不建議使用這方法

參考資料:
https://github.com/browscap/browscap/issues/119

二、使用Mobile-Detect類

https://github.com/serbanghita/Mobile-Detect
require "Mobile-Detect/Mobile_Detect.php";
$detect = new Mobile_Detect;
echo "\$detect->isMobile():".$detect->isMobile();

可以在php.ini裡面設定include_path去呼叫該類別。或是把該類別放到/usr/share/pear下
我的php.ini設定:
include_path = ".:/usr/share/pear"
更多Mobile-Detect的使用方法:
https://github.com/serbanghita/Mobile-Detect/wiki/Code-examples

三、使用phpbrowscap類別

https://github.com/GaretJax/phpbrowscap
安裝方法使用composer:
https://github.com/GaretJax/phpbrowscap/wiki/QuickStart
1. 在專案根目錄新增composer.json
{
    "require": {
        "garetjax/phpbrowscap": "~2.0"
    }
}
2.
$ wget http://getcomposer.org/composer.phar
$ php composer.phar install
如果這步有報錯
PHP Fatal error:  Class 'Phar' not found in /xxx/composer.phar on line xx
請將php.ini的
extension=phar.so 註解拿掉
安裝完成後目錄裡面會多出一個vendor的資料夾
新增一個test.php檔案:
<?php
require 'vendor/autoload.php'; //要用composer的類必須加入這行
use phpbrowscap\Browscap;
$bc = new Browscap('path/to/the/cache/dir'); //
$current_browser = $bc->getBrowser();
echo '<pre>'; // some formatting issues ;)
print_r($current_browser);
echo '</pre>';

因為刷http://localhost/test.php會刷很久刷不出來,所以放棄用第三個方式做

在FB的討論:
https://www.facebook.com/groups/199493136812961/permalink/713514665410803/
其他方法:
http://detectmobilebrowsers.com/mobile
http://www.useragentstring.com/pages/api.php #不建議使用,因為要去呼叫api
https://github.com/ventoviro/windwalker-environment #未測試
結論:
行動裝置太多樣了 幾個大牌子能正確偵測到已經夠了

2014年11月24日 星期一

linux安裝megatools和megacmd

在linux上能用指令下載mega檔案的工具有:
megatools
megacmd

系統:Debian 7

安裝megacmd

安裝megacmd難度比較低
1. 在github上下載megacmd-master.zip後解壓縮
2. 在解壓縮的資料夾下
$ make
$ cp megacmd /usr/local/bin
即安裝完成

使用megacmd
下載(需開一個帳號,然後將你要下載的檔案import到你的帳號裡面再下載,沒看到可以直接下載https連結的方法)
$ megacmd -force get mega:/testing/megacmd /tmp/
報錯:
ERROR: Downloading mega:/xxx.jpg failed (Object (typically, node or user) not found)
用wget檢查:
$ wget https://mega.xxx/
錯誤: “mega.xxx” 的证书不可信。
錯誤: “mega.xxx” 的证书颁发者未知。
... 無解,只好改用megatools

安裝megatools

方法一
把source.list改成unstable
deb http://ftp.cn.debian.org/debian unstable main contrib non-free
然後用apt-get安裝。但是我實在不想讓我的debian炸掉... 所以沒用這方法安裝
方法二
安裝所需的套件
# aptitude install libglib2.0-dev libcurl4-openssl-dev libssl-dev
不然./configure時會報錯
...
configure: error: Package requirements (gio-2.0 >= 2.32.0 libcurl openssl) were not met:
...
下載megatools的linux原始碼Archive(megatools-1.9.93.tar.gz),並解壓縮後到該資料夾下
$ ./configure
$ make
# make install
安裝完後就能使用megadl等相關mega指令了

下載
$ megadl 'https://mega.co.nz/#!xxx...'
報錯:
megadl: error while loading shared libraries: libmega.so.0: cannot open shared object file: No such file or directory
需要使用root執行一次ldconfig後才能正常下載
# ldconfig


參考資料:
http://blog.hbautista.com/linux/megatools-en-debian-jessie/ (西班牙文blog...請搭配google翻譯使用)

2014年11月23日 星期日

linux桌面安裝dropbox

OS: Debian 7

新申請的dropbox帳號後導會到安裝頁面:https://www.dropbox.com/install?os=lnx

推薦使用指令安裝,下載的deb檔我裝失敗(自動裝成64位元的,啟動不了)

請注意你系統是32bits還是64bits

官網寫的 cd ~ && wget -O - "https://www.dropbox.com/download?plat=lnx.x86" | tar xzf - 我執行會報錯,所以我把他分段執行...
$ cd ~
$ wget -O dropbox.tar.gz "https://www.dropbox.com/download?plat=lnx.x86"
$ tar zxvf dropbox.tar.gz

下載 CLI 指令碼(dropbox.py) 放到/usr/local/bin/下,記得把權限改成777

啟動dropbox(在有GFW干擾情況下,記得先設定proxychains)
$ proxychains ~/.dropbox-dist/dropboxd
查dropbox狀態
$ dropbox.py status



git同時push到兩個repo

情境:
以github和gitlab為例,假設他們各自有不同的內容要整合在一起

模擬環境
分別在github和gitlab建立新專案(ex 專案名稱mp),gitlab為master的pull
master 更新檔案 pull從gitlab
master 上傳檔案push到 gitlab和github(github純備份用,因為gitlab上是和其他人共同開發)

(分別在github和gitlab的mp.git新增不同的內容,我們之後要整合在一起)

拉下gitlab檔案
$ git clone git@xxx.tw:bear/mp.git gitlab_mp #用ssh要在gitlab設定keys,用https不用,但要輸入gitlab的帳號密碼
新增remote
$ git remote add github git@github.com:bear/mp.git
更新remote(remote branch會多remotes/github/master,用git branch -a 查詢)
$ git remote update

更新特定的remote

$ git remote update github

(這邊假設github和gitlab裡面各自有不同內容要整合,如果備份的repo為新開的repo可以略過a.b.c這三步)
a. 開github的branch
$ git checkout -b github remotes/github/master
b. 切回master
$ git checkout master
c. 將github整合進gitlab
$ git rebase github


git pull(做這步之後才能push,中間有conflict就手動改)
$ git pull #這步會多一個git merge的 commit
設定origin remote的url
$ git remote set-url origin --push --add git@xxx.tw:bear/mp2.git
$ git remote set-url origin --push --add git@github.com:bear/mp.git
檢查remote 會push到哪裡
$ git remote -v
github  git@github.com:bear/mp.git (fetch)
github  git@github.com:bear/mp.git (push)
origin  git@xxx.tw:bear/mp2.git (fetch)  # 因為git push預設是git push origin master,所以master會抓自架gitlab的repo
origin  git@xxx.tw:bear/mp2.git (push) # master會push到 gitlab
origin  git@github.com:bear/mp.git (push) # master也會push到 github
最後git push就能同時推到兩個不同的repo去了
$ git push

刷新gitlab和github頁面檢查

要更改預設master pull的repo
修改 .git/config 的
[remote "origin"]
    url = git@xxx.tw:bear/mp2.git #改成你要pull的repo

參考資料:
http://stackoverflow.com/questions/849308/pull-push-from-multiple-remote-locations 採用Malvineous的答案

關於刪除branch
移除gitlab上多餘的branch
$ git push origin --delete alt(多餘的branch名字)
本地的branch要分開刪,沒辦法一起刪
$ git branch -D alt
把本地remote的branch( git branch -a )也刪
# git branch --delete --remotes origin/alt

push新的branch到remote repository
$ git push origin exhibition:exhibition3
這樣遠端倉庫就會新建exhibition3分支,內容是本地端exhibition的內容,另外origin是你remote的名字

將遠端master branch拉到本地端exhibition branch
$ git pull origin master:exhibition
語法:
git pull <remote_name> <remote_branch>:<local_branch>

將本地端exhibition branch推到遠端master branch
$ git push origin exhibition:master
語法:
git push <remote_name> <local_branch>:<remote_branch>







2014年11月19日 星期三

debian gnome桌面顯示捷徑

系統:Debian 7 (wheezy)
桌面:gnome

開啟Advanced Settings
$ gnome-tweak-tool

左上角"應用程式" -> 系統工具 -> 偏好設定 -> 進階設定值

"桌面"分頁 -> 打開 "Have file manager handle the desktop"

如果還是沒有出現,打開"偏好的應用程式"GUI(左上角"應用程式"選單內我找不到,只能用指令開啟)
$ exo-preferred-applications
"公用程式"分頁 -> 檔案管理員 -> 選"Nautilus"

注意:
sublime的Preferences -> Browse Packages 預設檔案管理員要選"Thunar",不然打不開

新增捷徑:
在面板上按住alt點右鍵 -> 加入面板 -> 啟動圖示 -> 新增應用程式在面板後然後按ctrl複製拉到桌面

參考資料:
http://forums.debian.net/viewtopic.php?f=30&t=83012

linux查區網內有哪些ip

目標:
要查無線路由器內有多少機器上線,因為有時候無法開網進無線ap後台網頁看連線狀態,或者,有些無線路由器只列出dhcp的ip位址,固定ip位址沒列出來(ex. TP-Link TL-WR742N)。

google關鍵字搜尋:
linux ip scanner

工具:
arp-scan或nmap (推薦使用nmap)

安裝:(以arch linux為例)
# pacman -S arp-scan

# pacman -S nmap

使用:
arp-scan -
# arp-scan -l #我有兩張網卡(乙太網路和無線網路),只會列出乙太網路查詢的結果
# arp-scan 192.168.0.0/24 #Scans 192.168.0.0 255.255.255.0
# arp-scan 192.168.0.1-192.168.0.254 #Scans the obvious range

nmap -
# nmap -sP 192.168.199.0/24 #Scans 192.168.199.0 255.255.255.0
# nmap -sP 192.168.199.1-254 #Scans the obvious range

實測:
在檢查"極路由"路由器時(所有設備都連無線網路),arp-scan列出的結果過少,不正確
使用nmap列出的結果較多,但每次數量都不一樣。所以以列出數量那次為參考。

參考資料:
http://itswapshop.com/articles/top-3-ip-scanners-linux

arch 看syslog

什麼是syslog?
是 system log, 會紀錄誰執行了哪些東西, 有哪些 CRON 或者哪些動作正在被執行等紀錄.

在debian中看syslog:
# tail -f /var/log/syslog
在arch linux看syslog:
# journalctl -f

參考資料:
http://blog.longwin.com.tw/2011/11/linux-data-syslog-logger-2011/