为Ionic3+ (Angular4+)的项目配置nameof语法糖

熟悉C#的人应该知道,C# 6的新特性中包含一个名为nameof的关键字。使用该关键字可以不用实例化对象,即可获取到类成员变量的名字,比如:

public class ClassA
{
    public int fieldA;
    public string fieldB;
}

使用nameof(ClassA.fieldA)即可得到”fieldA”。虽然看起来很鸡肋,不过在应用了ORM的项目中,感觉还是很有用的。

而微软的另一个干儿子TypeScript则一直都没有类似的语法糖实现。

某老外便自己实现了基于TypeScript的nameof组件:

https://github.com/dsherret/ts-nameof

但想要应用在我自己的Ionic项目中,光有这个是不够的。

折腾了好久,总算勉强配置好了Ionic项目下的nameof的实现,步骤如下:

Step1:

安装ts-nameof

npm install ts-nameof --save-dev

Step2:

安装ts-nameof-loader(因为Ionic是基于WebPack打包的,所以需要这个WebPack的loader):

npm i ts-nameof-loader --save-dev

Step3:

复制项目根目录下的node_modules\@ionic\app-scripts\config\webpack.config.js到一个相对位置。比如在项目根目录下建立config文件夹,然后把webpack.config.js复制进去。

Step4:

修改复制出来的webpack.config.js文件,在Prod和Dev版本的loader中新增ts-nameof-loader,我的webpack.config.js文件内容如下:

/*
 * The webpack config exports an object that has a valid webpack configuration
 * For each environment name. By default, there are two Ionic environments:
 * "dev" and "prod". As such, the webpack.config.js exports a dictionary object
 * with "keys" for "dev" and "prod", where the value is a valid webpack configuration
 * For details on configuring webpack, see their documentation here
 * https://webpack.js.org/configuration/
 */

var path = require('path');
var webpack = require('webpack');
var ionicWebpackFactory = require(process.env.IONIC_WEBPACK_FACTORY);

var ModuleConcatPlugin = require('webpack/lib/optimize/ModuleConcatenationPlugin');
var PurifyPlugin = require('@angular-devkit/build-optimizer').PurifyPlugin;

var optimizedProdLoaders = [{
    test: /\.json$/,
    loader: 'json-loader'
  },
  {
    test: /\.js$/,
    loader: [{
        loader: process.env.IONIC_CACHE_LOADER
      },
      {
        loader: '@angular-devkit/build-optimizer/webpack-loader',
        options: {
          sourceMap: true
        }
      },
    ]
  },
  {
    test: /\.ts$/,
    use: [{
      loader: 'ts-nameof-loader'
    }]
  },
  {
    test: /\.ts$/,
    loader: [{
        loader: process.env.IONIC_CACHE_LOADER
      },
      {
        loader: '@angular-devkit/build-optimizer/webpack-loader',
        options: {
          sourceMap: true
        }
      },
      {
        loader: process.env.IONIC_WEBPACK_LOADER
      }
    ]
  }
];

function getProdLoaders() {
  if (process.env.IONIC_OPTIMIZE_JS === 'true') {
    return optimizedProdLoaders;
  }
  return devConfig.module.loaders;
}

var devConfig = {
  entry: process.env.IONIC_APP_ENTRY_POINT,
  output: {
    path: '{{BUILD}}',
    publicPath: 'build/',
    filename: '[name].js',
    devtoolModuleFilenameTemplate: ionicWebpackFactory.getSourceMapperFunction(),
  },
  devtool: process.env.IONIC_SOURCE_MAP_TYPE,

  resolve: {
    extensions: ['.ts', '.js', '.json'],
    modules: [path.resolve('node_modules')]
  },

  module: {
    loaders: [{
        test: /\.json$/,
        loader: 'json-loader'
      },
      {
        test: /\.ts$/,
        use: [{
          loader: 'ts-nameof-loader'
        }]
      },
      {
        test: /\.ts$/,
        loader: process.env.IONIC_WEBPACK_LOADER
      }
    ]
  },

  plugins: [
    ionicWebpackFactory.getIonicEnvironmentPlugin(),
    ionicWebpackFactory.getCommonChunksPlugin()
  ],

  // Some libraries import Node modules but don't use them in the browser.
  // Tell Webpack to provide empty mocks for them so importing them works.
  node: {
    fs: 'empty',
    net: 'empty',
    tls: 'empty'
  }
};

var prodConfig = {
  entry: process.env.IONIC_APP_ENTRY_POINT,
  output: {
    path: '{{BUILD}}',
    publicPath: 'build/',
    filename: '[name].js',
    devtoolModuleFilenameTemplate: ionicWebpackFactory.getSourceMapperFunction(),
  },
  devtool: process.env.IONIC_SOURCE_MAP_TYPE,

  resolve: {
    extensions: ['.ts', '.js', '.json'],
    modules: [path.resolve('node_modules')]
  },

  module: {
    loaders: getProdLoaders()
  },

  plugins: [
    ionicWebpackFactory.getIonicEnvironmentPlugin(),
    ionicWebpackFactory.getCommonChunksPlugin(),
    new ModuleConcatPlugin(),
    new PurifyPlugin()
  ],

  // Some libraries import Node modules but don't use them in the browser.
  // Tell Webpack to provide empty mocks for them so importing them works.
  node: {
    fs: 'empty',
    net: 'empty',
    tls: 'empty'
  }
};


module.exports = {
  dev: devConfig,
  prod: prodConfig
}

Step5:

修改项目package.json文件,覆盖默认webpack config,例如:

{
    /* ... */

    "config": {
        "ionic_webpack": "config/webpack.config.js"
    },

    /* ... */
}

Step6:

在项目中使用nameof关键字,并用console.log打印测试。

 

 

发表评论

此站点使用Akismet来减少垃圾评论。了解我们如何处理您的评论数据