Vesta can not add additional FTP

執行 v-add-web-domain-ftp 出現錯誤

  1. /usr/local/vesta/bin/v-add-web-domain-ftp: line 21: /func/main.sh: No such file or directory
  2. /usr/local/vesta/bin/v-add-web-domain-ftp: line 22: /func/domain.sh: No such file or directory
  3. /usr/local/vesta/bin/v-add-web-domain-ftp: line 23: /conf/vesta.conf: No such file or directory
  4. /usr/local/vesta/bin/v-add-web-domain-ftp: line 34: check_args: command not found
  5. /usr/local/vesta/bin/v-add-web-domain-ftp: line 35: validate_format: command not found
  6. /usr/local/vesta/bin/v-add-web-domain-ftp: line 36: is_system_enabled: command not found
  7. /usr/local/vesta/bin/v-add-web-domain-ftp: line 37: is_object_valid: command not found
  8. /usr/local/vesta/bin/v-add-web-domain-ftp: line 38: is_object_unsuspended: command not found
  9. /usr/local/vesta/bin/v-add-web-domain-ftp: line 39: is_object_valid: command not found
  10. /usr/local/vesta/bin/v-add-web-domain-ftp: line 40: is_object_unsuspended: command not found
  11. Error: ftp user _ already exists
  12. /usr/local/vesta/bin/v-add-web-domain-ftp: line 44: log_event: command not found

解決方法 ($VESTA 重新設定為 /usr/local/vesta)

  1. source /etc/profile
  2. cd /usr/local/vesta/bin
  3. ./v-add-web-domain-ftp [username] [domain] [ftp_user] [ftp_password] [relateive_pah]

由 Debian 7 升級到 8

  1. # 換成 root 用戶
  2. su -
  3.  
  4. # 切到下載目錄 (非必要)
  5. cd /root/download
  6.  
  7. # 先更新目前的系統
  8. apt-get update
  9. apt-get upgrade
  10.  
  11. # 取代源的代號,並嘗試再升級系統
  12. sed -i 's/wheezy/jessie/g' /etc/apt/sources.list
  13. apt-get update
  14. apt-get upgrade (如出現 ssh 請移除,否則會重啟 ssh 導致彈出連線)
  15. apt-get dist-upgrade --fix-missing
  16.  
  17. # 如無意外就進行重啟
  18. reboot
  19.  
  20. # 查看版本
  21. lsb_release -a

一道小題

  1.  有一個 Array 如下
  2.  
  3.  $dict = ['a' , 'b' , 'c' , 'd' , 'e' ];
  4.  
  5.  目前有一個變數 $i 控制想輸出的 Array
  6.  
  7.  當 $i = a 時回傳 abcde
  8.  當 $i = b 時回傳 bcdea
  9.  當 $i = d 時回傳 deabc
  10.  
  11.  怎麼寫比較漂亮?
  12.  想知道是否就只能用迴圈跑?

# 想到的解法如下

## 方法一 (直覺.但很多計算)

1. 取出目前 $i 值的位置
2. 取兩種 array (1. 由這位置取到尾, 2.再取 0 到這值置)
3. 最後將這兩種合起來

  1.  <?php
  2.  $dict = ['a' , 'b' , 'c' , 'd' , 'e'];
  3.  
  4.  $position    = array_search('c', $dict);
  5.  $totalSize   = count($dict);
  6.  $findOut     = array_slice($dict, $position, $totalSize);
  7.  $findOutSize = count($findOut);
  8.  
  9.  if ($findOutSize < $totalSize) {
  10.      $appendSize = $totalSize - $findOutSize;
  11.      $appendDict = array_slice($dict, 0, $appendSize);
  12.  }else{
  13.      $appendDict = [];
  14.  }
  15.  
  16.  print_r(array_merge($findOut, $appendDict));

## 方法二 (用遞歸.不算直覺.但快很多)

  1.  <?php
  2.  function genResult(array $dict, $startChar) {
  3.      if ($dict[0] === $startChar) return $dict;
  4.  
  5.      array_push($dict, array_shift($dict));
  6.     
  7.      return genResult($dict, $startChar);
  8.  }
  9.  
  10.  print_r(genResult(['a' , 'b' , 'c' , 'd' , 'e'], 'c'));

Lumen 安裝使用 Elixir

小筆記.直接進入主題

# 進入專案

  1. cd /path/to/lumen/project

# 安裝 gulp 和 laravel elixir package

  1. npm install gulp --save-dev
  2. npm install laravel-elixir --save-dev

# 放置 gulpfile.js

  1. touch gulpfile.js

# 添加以下內容到 gulpfile.js

DownLoad: gulpfile.js
  1.  var elixir = require('laravel-elixir'),
  2.      clean  = require('gulp-clean');
  3.  
  4.  // 設置 詳細可以打開 elixir 的 Config.js 參看
  5.  // elixir.config.sourcemaps = true;
  6.  // elixir.config.publicDir  = "public";
  7.  // elixir.config.assetsDir  = "resources/assets/";
  8.  // elixir.config.bowerDir   = "vendor/bower_components";
  9.  
  10.  // 自定義簡單的 task
  11.  gulp.task('clean', function () {
  12.      return gulp.src([
  13.          'public/foo',
  14.          'public/bar'
  15.      ])
  16.      .pipe(clean({ force: true }));
  17.  });
  18.  
  19.  // 自定義複雜的 task
  20.  elixir.extend("copySomething", function() {
  21.      gulp.task('copySomething', function() {
  22.          return gulp.src('resources/foo/bar/**/*').pipe(gulp.dest('public/foo/bar'));
  23.      });
  24.  
  25.      // 註冊到監控事件裡面,每次改動時指定檔案時都會觸發這個 task
  26.      this.registerWatcher('copySomething', "resources/foo/bar/**/*");
  27.  
  28.      return this.queueTask('copySomething');
  29.  });
  30.  
  31.  elixir(function(mix) {
  32.      mix.styles('app.css').scripts('app.js');
  33.  });

通過 Gandi API 查詢域名

直接記錄測試用的代碼.

package.json

DownLoad: package.json
  1.  {
  2.    "dependencies": {
  3.      "xmlrpc": "^1.3.0"
  4.    }
  5.  }

index.js

DownLoad: index.js
  1.  var xmlrpc = require('xmlrpc');
  2.  var apikey = '____YOUR____API___KEY___';
  3.  var words  = ['cut', 'daily', 'dance', 'danger', 'dark', 'date', 'day', 'dead', 'deal', 'death', 'decide', 'decision', 'declare', 'deep', 'defense', 'degree', 'demand', 'department', 'depend', 'dependent', 'describe', 'desire', 'destroy', 'detail', 'determine', 'develop', 'die', 'difference', 'different', 'difficult', 'difficulty', 'dinner', 'direct', 'direction', 'director', 'discover', 'discuss', 'discussion', '___YOUR___WORDS___ETC___'];
  4.  
  5.  var api = xmlrpc.createSecureClient({
  6.      host: 'rpc.ote.gandi.net', // 'rpc.gandi.net' for production
  7.      port: 443,
  8.      path: '/xmlrpc/'
  9.  });
  10.  
  11.  api.methodCall('version.info', [apikey], function (error, value) {
  12.      console.dir(value);
  13.  });
  14.  
  15.  function run(domain) {
  16.      var callback = function(error, value) {
  17.          console.log(new Date().toLocaleString());
  18.  
  19.          if (value[domain] == 'pending') {
  20.              setTimeout(function() {
  21.                  api.methodCall('domain.available', [apikey, [domain]], callback);
  22.              }, 700);
  23.          }else if (value[domain] == 'error_invalid') {
  24.              console.dir("Err - " + domain);
  25.          }else{
  26.              console.dir(value)
  27.          }
  28.      }
  29.  
  30.      api.methodCall('domain.available', [apikey, [domain]], callback)
  31.  }
  32.  
  33.  // Make sure the word length bigger than 2
  34.  // words = words.filter(function(word) {
  35.  //     return word.length > 2;
  36.  // });
  37.  
  38.  words.some(function(word) {
  39.      run(word + ".xyz");
  40.  });

Golang 創解文件和追加內容

朋友的問題.雖然這玩意只玩過一次.
但還是為這問題再去玩了一下.順道筆記一下

  1.  package main
  2.  
  3.  import (
  4.      "os"
  5.      "io/ioutil"
  6.  )
  7.  
  8.  const (
  9.      FILENAME = "test.txt"
  10.  )
  11.  
  12.  func createFile() {
  13.      file, err := os.Create(FILENAME)
  14.  
  15.      if err != nil {
  16.          panic(err)
  17.      }
  18.  
  19.      defer file.Close()
  20.  }
  21.  
  22.  func appendContent() {
  23.      file, openErr := os.OpenFile(FILENAME, os.O_APPEND | os.O_WRONLY, 0666)
  24.  
  25.      if openErr != nil {
  26.          panic(openErr)
  27.      }
  28.  
  29.      defer file.Close()
  30.  
  31.      _, writeErr := file.WriteString("This is a test content 1\n")
  32.  
  33.      if writeErr != nil {
  34.          panic(writeErr)
  35.      }
  36.  }
  37.  
  38.  func exampleForIOUtilWriteFile() {
  39.      ioutil.WriteFile(FILENAME, []byte("This is a test content 2\n"), os.ModeAppend)
  40.  }
  41.  
  42.  func main() {
  43.  
  44.      _, err := os.Stat(FILENAME)
  45.  
  46.      if os.IsNotExist(err) {
  47.          createFile()
  48.      }
  49.  
  50.      appendContent()
  51.      // exampleForIOUtilWriteFile()
  52.  }

Python PIL 1.5 小記

安裝一個舊的程式.
在安裝套件時發現 PIL 出錯.
找大神問了一下.發現是 PIL 1.5 版本問題.
因為 PIL 引用了外部的源.所以下載不了.
解決方法有幾個記錄一下

執行

  1. pip install -r requirements.txt

得到

  1.  Downloading/unpacking PIL
  2.    Could not find any downloads that satisfy the requirement PIL
  3.    Some externally hosted files were ignored (use --allow-external PIL to allow).
  4.  Cleaning up...
  5.  No distributions at all found for PIL

解決 1

  1. pip install PIL --allow-external PIL --allow-unverified PIL

解決 2

  1. pip install Pillow

將對應的

  1.  import Image

換成

  1.  from PIL import Image

用 Exim4 來發送郵件

因為某些奇怪的原因.所以沒帶 sendmail 這東西.
再者不想加入這麼大型的玩意到目前的機械上.
所以直接裝上 Exim4 為機械發送郵件.
而別的東西還是留在 Mailgun 上.
筆記一下 (機械為 Debian 7 i386)

先確認移除 sendmail (如本身沒有可不用)

  1. invoke-rc.d sendmail stop
  2. apt-get -q -y remove --purge "sendmail*"
  3. apt-get clean

裝上 Exim4 (同時設為可以對外)

  1. which mail
  2. apt-get -q -y install "exim4"
  3. apt-get clean
  4. ls /etc/exim4/update-exim4.conf.conf
  5. sed -i "s/dc_eximconfig_configtype='local'/dc_eximconfig_configtype='internet'/" /etc/exim4/update-exim4.conf.conf
  6. cat /etc/exim4/update-exim4.conf.conf | grep dc_eximconfig_configtype
  7. invoke-rc.d exim4 restart

如果發送郵件後發現沒收到郵件.可以查看 log

  1. tail -n 10 /var/log/exim4/mainlog

在 Laravel 查詢中 setTablePrefix

目前遇到的情況是.有一個表.但需要在裡面存不同語系的資料.
如 en_us_message, zh_tw_message, zh_cn_message.
除了建立新的 ORM Model 外.好像就沒方法在 ORM 查詢時更改表名.
當然可以用 DB::table Query 來查詢.但寫法比較長.
最後只好找了一下和改了一下找回來的方法

1. 建立一個 Factory 來生成 Model 並在生成時設置他的對應表名
2. 在查詢時使用 ModelFactory::fromTable(ModelName, TableName) 解決

但問題是.這種生成會導致 create 和 all 這類方法失效.
失效指的是他不能夠使用指的 TableName.
原因是這些方法會自已生成 Model (new static) 而不用現有的 instance.

當然.除了這種方法還可以考慮用 laravel-translatable 這玩意

筆記一下

工廠類

  1.  <?php
  2.  class ModelFactory extends Eloquent {
  3.  
  4.      protected static $_table;
  5.  
  6.      public static function fromTable($model, $table, $attributes = Array()) {
  7.          $instance = null;
  8.  
  9.          if (class_exists($model) === true) {
  10.              $instance = new $model($attributes);
  11.              $instance->setTable($table);
  12.          } else {
  13.              $instance = new static($attributes);
  14.              $instance->setTable($table);
  15.          }
  16.  
  17.          return $instance;
  18.      }
  19.  
  20.      public function setTable($table) {
  21.          static::$_table = $table;
  22.      }
  23.  
  24.      public function getTable() {
  25.          return static::$_table;
  26.      }
  27.  
  28.  }

使用方法

  1.  <?php
  2.  Route::get('/', function() {
  3.      // Do not use create, all method (it will new object can not overwrite prefix)
  4.  
  5.      $langs = ['en_us', 'zh_tw', 'zh_cn'];
  6.  
  7.      foreach($langs as $lang) {
  8.          $table = $lang.'_message';
  9.  
  10.          ModelFactory::fromTable('message', $table)->fill([
  11.              'content' => 'content_'.$lang
  12.          ])->save();
  13.      }
  14.  
  15.      foreach($langs as $lang) {
  16.          $table = $lang.'_message';
  17.  
  18.          $messages = ModelFactory::fromTable('message', $table)->get();
  19.  
  20.          echo "<h3>".$lang."</h3>";
  21.          foreach($messages as $message) {
  22.              echo "<p>".$message->content."</p>";
  23.          }
  24.      }
  25.  
  26.  });

資料庫結構

  1.  <?php
  2.  
  3.  use Illuminate\Database\Schema\Blueprint;
  4.  use Illuminate\Database\Migrations\Migration;
  5.  
  6.  class CreateMessageTable extends Migration {
  7.  
  8.      /**
  9.       * Run the migrations.
  10.       *
  11.       * @return void
  12.       */
  13.      public function up()
  14.      {
  15.          Schema::create('en_us_message', function($table) {
  16.              $table->increments('id');
  17.              $table->string('content', 100);
  18.              $table->timestamps();
  19.          });
  20.  
  21.          Schema::create('zh_tw_message', function($table) {
  22.              $table->increments('id');
  23.              $table->string('content', 100);
  24.              $table->timestamps();
  25.          });
  26.  
  27.          Schema::create('zh_cn_message', function($table) {
  28.              $table->increments('id');
  29.              $table->string('content', 100);
  30.              $table->timestamps();
  31.          });
  32.      }
  33.  
  34.      /**
  35.       * Reverse the migrations.
  36.       *
  37.       * @return void
  38.       */
  39.      public function down()
  40.      {
  41.          Schema::dropIfExists('en_us_message');
  42.          Schema::dropIfExists('zh_tw_message');
  43.          Schema::dropIfExists('zh_cn_message');
  44.      }
  45.  
  46.  }

在推裡取得某個列表的最新推文

由於某種特別的取求.所以必需在用戶的 Twitter 帳戶裡面.
取得這個用戶中被指定的列表內容.而這內容則為最新推文
記錄一下用 Tweepy 實測的代碼

  1.  #!/usr/bin/python
  2.  # -*- coding: utf-8 -*-
  3.  
  4.  import tweepy
  5.  
  6.  class Taut(object):
  7.     
  8.      def __init__(self, consumer_key=None, consumer_secret=None, access_token_key=None, access_token_secret=None):
  9.          auth = tweepy.OAuthHandler(consumer_key, consumer_secret)
  10.          auth.set_access_token(access_token_key, access_token_secret)
  11.         
  12.          self.api = tweepy.API(auth)
  13.         
  14.      def show_list(self):
  15.          r = self.api.lists_all()
  16.         
  17.          for item in r:
  18.              print("{0}, {1}, {2}".format(item.name, item.slug, item.id_str))
  19.  
  20.      def show_target_list(self, list_id, slug):
  21.          r = self.api.list_timeline(list_id=list_id, slug=slug)
  22.         
  23.          for item in r:                           
  24.              print "> ID        : {0}".format(item.id)
  25.              print "> Name      : {0}".format(item.user.name.encode("UTF-8"))
  26.              print "> ScreenName: {0}".format(item.user.screen_name.encode("UTF-8"))
  27.              print "> Text:\n{0}".format(item.text.encode("UTF-8"))
  28.             
  29.              if hasattr(item, 'extended_entities'):
  30.                  extended_entities = item.extended_entities
  31.                 
  32.                  if 'media' in extended_entities:
  33.                      print "> Media:"
  34.                      for media in extended_entities['media']:
  35.                          print "--- {0}".format(media['media_url'])
  36.                         
  37.              print "======"
  38.  
  39.      def single_entities(self, item):
  40.          entities = item.entities
  41.             
  42.          print entities
  43.         
  44.          if 'urls' in entities:
  45.              print "------urls"
  46.              print len(entities['urls'])
  47.             
  48.              for url in entities['urls']:
  49.                  print "- {0}".format(url['url'])
  50.         
  51.          if 'media' in entities:
  52.              print "------media"
  53.              print len(entities['media'])
  54.             
  55.              for media in entities['media']:
  56.                  print "- {0}".format(media['media_url'])
  57.         
  58.                  print "++++++++++++++++++++++++++"
  59.             
  60.  if __name__ == "__main__":
  61.      taut = Taut(
  62.          consumer_key="YOU_KEY",
  63.          consumer_secret="YOU_KEY",
  64.          access_token_key="YOU_KEY",
  65.          access_token_secret="YOU_KEY"
  66.      )
  67.     
  68.      taut.show_list()
  69.      taut.show_target_list(LIST_ID, SLUG)
  70.      taut.show_target_list(LIST_ID, SLUG)

© 2015 不記程式

Theme by Anders NorenUp ↑

Fork me on GitHub