かもメモ

自分の落ちた落とし穴に何度も落ちる人のメモ帳

Gulp min化したJS・CSSに自動でコメントを入れたい

f:id:kikiki-kiki:20161129005159p:plain コーディングをする時、Gulpでコンパイル&min化をしています。
min化したコードにコメントでバージョン情報とか、元のライセンス情報を入れたいケースとかがあります。

javascript

ライブラリなどのライセンス情報で/*!で始まるコメントの場合はgulp-uglifyのオプションでmin化する際に残すことができるみたいです。

var gulp = require('gulp'),
    rename = require('gulp-rename'),
    // console.logを削除するパッケージ
    stripDebug = require("gulp-strip-debug"),
    // jsをmin化するパッケージ
    uglify = require("gulp-uglify");

gulp.task('js. minify', function(cb) {
  return gulp.src( FILE_PATH )
    .pipe( stripDebug() )
    .pipe( uglify({
      // このオプションを使うと/*! */のコメントは残る
      preserveComments: 'some'
    }) )
    .pipe( rename({
      extname: '.min.js'
    }) )
    .pipe( gulp.dest( DEST_DIR ) );
});
/*! License */

↑ この/*!で始まる形式でないコメントは消えてしまうので、違う形式でライセンスが書かれているファイルはライセンスのコメントを残すことができないので注意が必要。

CSS

いつもCSSのmin化につかっているgulp-clean-cssでは特定の形式のコメントを残す方法が無さそうでした…
ライセンス情報を残すオプションのある良い感じのライブラリがあれば教えてください。

ファイルの先頭にテキストを追加できるパッケージを使う


gulp-header を利用すればJS, CSSに関わらず好きなコメントをファイルの先頭に追加できるようです。
min化したファイルに最後にバージョン情報や最終更新日時を追加するのに良さそうです。

ex: min化したCSSにpackage.jsonに書かれている情報を元にコメントを追加する

var gulp = require("gulp"),
    rename = require('gulp-rename'),
    header = require('gulp-header'),
    cssminify = require('gulp-clean-css'),
    // 日付を簡単にフォーマットできるパッケージ
    moment = require('moment');

// package.jsonを読み込む
var pkg = require('./package.json');
// CSSに追加するテキスト
var banner = ['/**',
    ' * <%= pkg.name %>',
    ' * @version <%= pkg.version %>',
    ' * @author <%= pkg.author %>',
    ' * @lastmodified <%= today %>',
    ' */',
    ''].join('\n');


gulp.task('css.minify', function(cb) {
  var versionDate = moment().format('YYYY-MM-DD');

  return gulp.src( FILE_PATH )
    .pipe( cssminify() )
    .pipe( rename({
      extname: '.min.css'
    }) )
    .pipe( header(banner, {
      pkg: pkg,
       today: versionDate
     }) )
    .pipe( gulp.dest( DEST_DIR ) );
});

gulp css.minifyでタスクを実行すると、min化されたCSSファイルの先頭に下記のようなコメントが追加されます。

/**
 * PROJECT-NAME
 * @version 1.0.0
 * @author KiKiKi_KiKi
 * @lastmodified 2016-11-29
 */

 

完璧にライブラリなどに書かれたライセンス情報のコメントを自動的に残す方法は達成できませんでしたが、JSではuglifyのオプションを利用すればそれなりに上手く行きそうな気がします。
また、gulp-headerを使えばプロジェクトの情報などを動的に追加することができるので、CSSでも追加するコメントのテンプレートを予め作成しておけば、ある程度カバーできそうだなぁと思いました。


[参考]

速習ECMAScript6: 次世代の標準JavaScriptを今すぐマスター!

速習ECMAScript6: 次世代の標準JavaScriptを今すぐマスター!

PHP Slim 2.x Ajaxでputで送った値を取得したい。

"Slim is a PHP micro-framework" Rubyのテンプレートエンジンじゃない娘のお話です。

3系が既に出ているのですが、先方のサーバーのPHPのバージョンの関係で2系で開発をしています。今回 Ajaxのputメソッドでデータを送ったのですが、Slim側で値をとるのに少しハマったのでメモ。

Ajaxを送る側はこんな感じ

$(function () {
  var appAPI = {
    update: function(id, data) {
      var defer = $.Deferred(),
          apiPath = '/api/item/';
      $.ajax({
        type: 'PUT',
        url: apiPath + id,
        data: data,
        dataType: 'json',
        success: defer.resolve,
        error: defer.reject
      });
      return defer.promise();
    },
  };
  
  // 編集を保存する時に実行される関数
  var onEdited = function(itemID) {
    var formData = $('#my-form').serialize();
    appAPI.update(itemID, formData)
      .done(function(res) {
        // SECCESS
      })
      .fail(function(XMLHttpRequest, status, errorThrow) {
        // ERROR
      });
    return;
  };
});

Slimの設定

<?php
require('./vendor/autoload.php');

class MyAPP {
  public $slim;

  public function __construct() {
    $this->slim = new \Slim\Slim();
    $this->setupRouter();
  }

  // Routing
  private function setupRouter() {
    // API
    $this->slim->get('/api/item/:id', array($this, 'getItemByID'));
    $this->slim->post('/api/item', array($this, 'insertItem'));
    $this->slim->put('/api/item/:id', array($this, 'updateItem'));
    $this->slim->delete('/api/item/:id', array($this, 'deleteItem'));
  }
  
  // GET
  public function getItemByID($id) {
  }
  
  // POST
  public function insertItem() {
    // Ajaxから送られてきたデータは $_POST で配列形式で取得できる
    $postData = $_POST;
  }
  
  // PUT
  public function updateItem($id) {
    // Ajaxから送られたデータ $_POST は空配列隣取得できない。
    // Slimの機能を使って取得する
    $res = $this->slim->request();
    // getBody() で取得できるデータは `id=1&name=job1&...`のような形式になる
    $postData = $res->getBody();
    // parse_str で配列に変換する
    parse_str($postData, $postDataArray);
  }
  
  // DELETE
  public function deleteItem($id) {
  }

  public function run(){
    $this->slim->run();
  }
}

$myAPP = new MyApp();
$myAPP->run();

Ajax側から$form.serializeArray()で送れば、Slim側ではjson形式で取得できるのではないか?
と思って試してみたのですが、$res->getBody()で取得できる値は&つなぎの文字列になっていて、json_decode()で配列にすることはできませんでした。メソッドによって取得できる値の形式が異なるとメンドーなので、ぜんぶjson形式で取得できるのが楽なのですが...
もしかすると、Ajaxで送信するデータを自前でjson形式にしてしまうと、Slim側の$res->getBody()で取得できる値もjson形式になるかもしれません。


javascript 確認ダイアログ(confirm)の文章を改行させたい。

削除するとか、元に戻せない動作を行う前には誤動作の可能性を考慮して、確認ダイアログを入れるのが好ましいと思っています。
独自実装しても良いのですが、デザインが無かったりで、とりあえずサクット作ってしまっておきたい場合はデフォルトのwindow.confirm()を使うことが多いです。
で、このデフォルトのconfirmで表示させる文字を改行させたい時は\nを入れればOK。(HTMLタグは効かなきので<br>とか書いてもそのまま表示されます。)

コードを書くとこんな感じです。

if( window.confirm('この動作は元に戻せません。\n那珂ちゃんのファンを辞めますか?') ) {
  // 那珂ちゃんのファンを辞める処理
}

サンプル

那珂ちゃんのファンを辞める


エンコードする時に便利です。