<commit_before>let path = require('path');
let glob = require('glob');
let webpack = require('webpack');
let Mix = require('laravel-mix').config;
let webpackPlugins = require('laravel-mix').plugins;

/*
 |--------------------------------------------------------------------------
 | Mix Initialization
 |--------------------------------------------------------------------------
 |
 | As our first step, we'll require the project's Laravel Mix file
 | and record the user's requested compilation and build steps.
 | Once those steps have been recorded, we may get to work.
 |
 */

Mix.initialize();

/*
 |--------------------------------------------------------------------------
 | Webpack Context
 |--------------------------------------------------------------------------
 |
 | This prop will determine the appropriate context, when running Webpack.
 | Since you have the option of publishing this webpack.config.js file
 | to your project root, we will dynamically set the path for you.
 |
 */

module.exports.context = Mix.Paths.root();

/*
 |--------------------------------------------------------------------------
 | Webpack Entry
 |--------------------------------------------------------------------------
 |
 | We'll first specify the entry point for Webpack. By default, we'll
 | assume a single bundled file, but you may call Mix.extract()
 | to make a separate bundle specifically for vendor libraries.
 |
 */

module.exports.entry = Mix.entry();

/*
 |--------------------------------------------------------------------------
 | Webpack Output
 |--------------------------------------------------------------------------
 |
 | Webpack naturally requires us to specify our desired output path and
 | file name. We'll simply echo what you passed to with Mix.js().
 | Note that, for Mix.version(), we'll properly hash the file.
 |
 */

module.exports.output = Mix.output();

/*
 |--------------------------------------------------------------------------
 | Rules
 |--------------------------------------------------------------------------
 |
 | Webpack rules allow us to register any number of loaders and options.
 | Out of the box, we'll provide a handful to get you up and running
 | as quickly as possible, though feel free to add to this list.
 |
 */

let plugins = [];

if (Mix.options.extractVueStyles) {
    var vueExtractTextPlugin = Mix.vueExtractTextPlugin();

    plugins.push(vueExtractTextPlugin);
}

let rules = [
    {
        test: /\.vue$/,
        loader: 'vue-loader',
        options: {
            loaders: Mix.options.extractVueStyles ? {
                js: 'babel-loader' + Mix.babelConfig(),
                scss: vueExtractTextPlugin.extract({
                    use: 'css-loader!sass-loader',
                    fallback: 'vue-style-loader'
                }),
                sass: vueExtractTextPlugin.extract({
                    use: 'css-loader!sass-loader?indentedSyntax',
                    fallback: 'vue-style-loader'
                }),
                stylus: vueExtractTextPlugin.extract({
                    use: 'css-loader!stylus-loader?paths[]=node_modules',
                    fallback: 'vue-style-loader'
                }),
                css: vueExtractTextPlugin.extract({
                    use: 'css-loader',
                    fallback: 'vue-style-loader'
                })
            }: {
                js: 'babel-loader' + Mix.babelConfig(),
                scss: 'vue-style-loader!css-loader!sass-loader',
                sass: 'vue-style-loader!css-loader!sass-loader?indentedSyntax',
                stylus: 'vue-style-loader!css-loader!stylus-loader?paths[]=node_modules'
            },

            postcss: Mix.options.postCss
        }
    },

    {
        test: /\.jsx?$/,
        exclude: /(node_modules|bower_components)/,
        loader: 'babel-loader' + Mix.babelConfig()
    },

    {
        test: /\.css$/,
        loaders: ['style-loader', 'css-loader']
    },

    {
        test: /\.s[ac]ss$/,
        include: /node_modules/,
        loaders: ['style-loader', 'css-loader', 'sass-loader']
    },

    {
        test: /\.html$/,
        loaders: ['html-loader']
    },

    {
        test: /\.(png|jpe?g|gif)$/,
        loaders: [
            {
                loader: 'file-loader',
                options: {
                    name: path => {
                        if (! /node_modules|bower_components/.test(path)) {
                            return 'images/[name].[ext]?[hash]';
                        }

                        return 'images/vendor/' + path
                            .replace(/\\/g, '/')
                            .replace(
                                /((.*(node_modules|bower_components))|images|image|img|assets)\//g, ''
                            ) + '?[hash]';
                    },
                    publicPath: Mix.options.resourceRoot
                }
            },
            'img-loader'
        ]
    },

    {
        test: /\.(woff2?|ttf|eot|svg|otf)$/,
        loader: 'file-loader',
        options: {
            name: path => {
                if (! /node_modules|bower_components/.test(path)) {
                    return 'fonts/[name].[ext]?[hash]';
                }

                return 'fonts/vendor/' + path
                    .replace(/\\/g, '/')
                    .replace(
                        /((.*(node_modules|bower_components))|fonts|font|assets)\//g, ''
                    ) + '?[hash]';
            },
            publicPath: Mix.options.resourceRoot
        }
    },

    {
        test: /\.(cur|ani)$/,
        loader: 'file-loader',
        options: {
            name: '[name].[ext]?[hash]',
            publicPath: Mix.options.resourceRoot
        }
    }
];

if (Mix.preprocessors) {
    Mix.preprocessors.forEach(preprocessor => {
        rules.push(preprocessor.rules());

        plugins.push(preprocessor.extractPlugin);
    });
}

module.exports.module = { rules }

/*
 |--------------------------------------------------------------------------
 | Resolve
 |--------------------------------------------------------------------------
 |
 | Here, we may set any options/aliases that affect Webpack's resolving
 | of modules. To begin, we will provide the necessary Vue alias to
 | load the Vue common library. You may delete this, if needed.
 |
 */

module.exports.resolve = {
    extensions: ['*', '.js', '.jsx', '.vue'],

    alias: {
        'vue$': 'vue/dist/vue.common.js'
    }
};

/*
 |--------------------------------------------------------------------------
 | Stats
 |--------------------------------------------------------------------------
 |
 | By default, Webpack spits a lot of information out to the terminal,
 | each you time you compile. Let's keep things a bit more minimal
 | and hide a few of those bits and pieces. Adjust as you wish.
 |
 */

module.exports.stats = {
    hash: false,
    version: false,
    timings: false,
    children: false,
    errors: false
};

process.noDeprecation = true;

module.exports.performance = { hints: false };

/*
 |--------------------------------------------------------------------------
 | Devtool
 |--------------------------------------------------------------------------
 |
 | Sourcemaps allow us to access our original source code within the
 | browser, even if we're serving a bundled script or stylesheet.
 | You may activate sourcemaps, by adding Mix.sourceMaps().
 |
 */

module.exports.devtool = Mix.sourcemaps;

/*
 |--------------------------------------------------------------------------
 | Webpack Dev Server Configuration
 |--------------------------------------------------------------------------
 |
 | If you want to use that flashy hot module replacement feature, then
 | we've got you covered. Here, we'll set some basic initial config
 | for the Node server. You very likely won't want to edit this.
 |
 */
module.exports.devServer = {
    historyApiFallback: true,
    noInfo: true,
    compress: true,
    quiet: true
};

/*
 |--------------------------------------------------------------------------
 | Plugins
 |--------------------------------------------------------------------------
 |
 | Lastly, we'll register a number of plugins to extend and configure
 | Webpack. To get you started, we've included a handful of useful
 | extensions, for versioning, OS notifications, and much more.
 |
 */

plugins.push(
    new webpack.ProvidePlugin(Mix.autoload || {}),

    new webpackPlugins.FriendlyErrorsWebpackPlugin({ clearConsole: Mix.options.clearConsole }),

    new webpackPlugins.StatsWriterPlugin({
        filename: 'mix-manifest.json',
        transform: Mix.manifest.transform.bind(Mix.manifest),
    }),

    new webpack.LoaderOptionsPlugin({
        minimize: Mix.inProduction,
        options: {
            postcss: Mix.options.postCss,
            context: __dirname,
            output: { path: './' }
        }
    })
);

if (Mix.browserSync) {
    plugins.push(
        new webpackPlugins.BrowserSyncPlugin(
            Object.assign({
                host: 'localhost',
                port: 3000,
                proxy: 'app.dev',
                files: [
                    'app/**/*.php',
                    'resources/views/**/*.php',
                    'public/js/**/*.js',
                    'public/css/**/*.css'
                ]
            }, Mix.browserSync),
            {
                reload: false
            }
        )
    );
}

if (Mix.options.notifications) {
    plugins.push(
        new webpackPlugins.WebpackNotifierPlugin({
            title: 'Laravel Mix',
            alwaysNotify: true,
            contentImage: Mix.Paths.root('node_modules/laravel-mix/icons/laravel.png')
        })
    );
}

if (Mix.copy) {
    Mix.copy.forEach(copy => {
        plugins.push(
            new webpackPlugins.CopyWebpackPlugin([copy])
        );
    });
}

if (Mix.extract) {
    plugins.push(
        new webpack.optimize.CommonsChunkPlugin({
            names: Mix.entryBuilder.extractions,
            minChunks: Infinity
        })
    );
}

if (Mix.options.versioning) {
    plugins.push(
        new webpack[Mix.inProduction ? 'HashedModuleIdsPlugin': 'NamedModulesPlugin'](),
        new webpackPlugins.WebpackChunkHashPlugin()
    );
}

if (Mix.options.purifyCss) {
    let PurifyCSSPlugin = require('purifycss-webpack');

    // By default, we'll scan all Blade and Vue files in our project.
    let paths = glob.sync(Mix.Paths.root('resources/views/**/*.blade.php')).concat(
        Mix.js.reduce((carry, js) => {
            return carry.concat(glob.sync(js.entry.map(entry => entry.base) + '/**/*.vue'));
        }, [])
    );

    plugins.push(new PurifyCSSPlugin(
        Object.assign({ paths }, Mix.options.purifyCss, { minimize: Mix.inProduction })
    ));
}

if (Mix.inProduction) {
    plugins.push(
        new webpack.DefinePlugin({
            'process.env': {
                NODE_ENV: '"production"'
            }
        }),

        new webpack.optimize.UglifyJsPlugin(Mix.options.uglify)
    );
}

plugins.push(
    new webpackPlugins.WebpackOnBuildPlugin(
        stats => Mix.events.fire('build', stats)
    )
);

module.exports.plugins = plugins;

/*
 |--------------------------------------------------------------------------
 | Mix Finalizing
 |--------------------------------------------------------------------------
 |
 | Now that we've declared the entirety of our Webpack configuration, the
 | final step is to scan for any custom configuration in the Mix file.
 | If mix.webpackConfig() is called, we'll merge it in, and build!
 |
 */

if (Mix.webpackConfig) {
    module.exports = require('webpack-merge').smart(
        module.exports, Mix.webpackConfig
    );
}
<commit_msg>Allow for disabling uglification - closes #563<commit_after>let path = require('path');
let glob = require('glob');
let webpack = require('webpack');
let Mix = require('laravel-mix').config;
let webpackPlugins = require('laravel-mix').plugins;

/*
 |--------------------------------------------------------------------------
 | Mix Initialization
 |--------------------------------------------------------------------------
 |
 | As our first step, we'll require the project's Laravel Mix file
 | and record the user's requested compilation and build steps.
 | Once those steps have been recorded, we may get to work.
 |
 */

Mix.initialize();

/*
 |--------------------------------------------------------------------------
 | Webpack Context
 |--------------------------------------------------------------------------
 |
 | This prop will determine the appropriate context, when running Webpack.
 | Since you have the option of publishing this webpack.config.js file
 | to your project root, we will dynamically set the path for you.
 |
 */

module.exports.context = Mix.Paths.root();

/*
 |--------------------------------------------------------------------------
 | Webpack Entry
 |--------------------------------------------------------------------------
 |
 | We'll first specify the entry point for Webpack. By default, we'll
 | assume a single bundled file, but you may call Mix.extract()
 | to make a separate bundle specifically for vendor libraries.
 |
 */

module.exports.entry = Mix.entry();

/*
 |--------------------------------------------------------------------------
 | Webpack Output
 |--------------------------------------------------------------------------
 |
 | Webpack naturally requires us to specify our desired output path and
 | file name. We'll simply echo what you passed to with Mix.js().
 | Note that, for Mix.version(), we'll properly hash the file.
 |
 */

module.exports.output = Mix.output();

/*
 |--------------------------------------------------------------------------
 | Rules
 |--------------------------------------------------------------------------
 |
 | Webpack rules allow us to register any number of loaders and options.
 | Out of the box, we'll provide a handful to get you up and running
 | as quickly as possible, though feel free to add to this list.
 |
 */

let plugins = [];

if (Mix.options.extractVueStyles) {
    var vueExtractTextPlugin = Mix.vueExtractTextPlugin();

    plugins.push(vueExtractTextPlugin);
}

let rules = [
    {
        test: /\.vue$/,
        loader: 'vue-loader',
        options: {
            loaders: Mix.options.extractVueStyles ? {
                js: 'babel-loader' + Mix.babelConfig(),
                scss: vueExtractTextPlugin.extract({
                    use: 'css-loader!sass-loader',
                    fallback: 'vue-style-loader'
                }),
                sass: vueExtractTextPlugin.extract({
                    use: 'css-loader!sass-loader?indentedSyntax',
                    fallback: 'vue-style-loader'
                }),
                stylus: vueExtractTextPlugin.extract({
                    use: 'css-loader!stylus-loader?paths[]=node_modules',
                    fallback: 'vue-style-loader'
                }),
                css: vueExtractTextPlugin.extract({
                    use: 'css-loader',
                    fallback: 'vue-style-loader'
                })
            }: {
                js: 'babel-loader' + Mix.babelConfig(),
                scss: 'vue-style-loader!css-loader!sass-loader',
                sass: 'vue-style-loader!css-loader!sass-loader?indentedSyntax',
                stylus: 'vue-style-loader!css-loader!stylus-loader?paths[]=node_modules'
            },

            postcss: Mix.options.postCss
        }
    },

    {
        test: /\.jsx?$/,
        exclude: /(node_modules|bower_components)/,
        loader: 'babel-loader' + Mix.babelConfig()
    },

    {
        test: /\.css$/,
        loaders: ['style-loader', 'css-loader']
    },

    {
        test: /\.s[ac]ss$/,
        include: /node_modules/,
        loaders: ['style-loader', 'css-loader', 'sass-loader']
    },

    {
        test: /\.html$/,
        loaders: ['html-loader']
    },

    {
        test: /\.(png|jpe?g|gif)$/,
        loaders: [
            {
                loader: 'file-loader',
                options: {
                    name: path => {
                        if (! /node_modules|bower_components/.test(path)) {
                            return 'images/[name].[ext]?[hash]';
                        }

                        return 'images/vendor/' + path
                            .replace(/\\/g, '/')
                            .replace(
                                /((.*(node_modules|bower_components))|images|image|img|assets)\//g, ''
                            ) + '?[hash]';
                    },
                    publicPath: Mix.options.resourceRoot
                }
            },
            'img-loader'
        ]
    },

    {
        test: /\.(woff2?|ttf|eot|svg|otf)$/,
        loader: 'file-loader',
        options: {
            name: path => {
                if (! /node_modules|bower_components/.test(path)) {
                    return 'fonts/[name].[ext]?[hash]';
                }

                return 'fonts/vendor/' + path
                    .replace(/\\/g, '/')
                    .replace(
                        /((.*(node_modules|bower_components))|fonts|font|assets)\//g, ''
                    ) + '?[hash]';
            },
            publicPath: Mix.options.resourceRoot
        }
    },

    {
        test: /\.(cur|ani)$/,
        loader: 'file-loader',
        options: {
            name: '[name].[ext]?[hash]',
            publicPath: Mix.options.resourceRoot
        }
    }
];

if (Mix.preprocessors) {
    Mix.preprocessors.forEach(preprocessor => {
        rules.push(preprocessor.rules());

        plugins.push(preprocessor.extractPlugin);
    });
}

module.exports.module = { rules }

/*
 |--------------------------------------------------------------------------
 | Resolve
 |--------------------------------------------------------------------------
 |
 | Here, we may set any options/aliases that affect Webpack's resolving
 | of modules. To begin, we will provide the necessary Vue alias to
 | load the Vue common library. You may delete this, if needed.
 |
 */

module.exports.resolve = {
    extensions: ['*', '.js', '.jsx', '.vue'],

    alias: {
        'vue$': 'vue/dist/vue.common.js'
    }
};

/*
 |--------------------------------------------------------------------------
 | Stats
 |--------------------------------------------------------------------------
 |
 | By default, Webpack spits a lot of information out to the terminal,
 | each you time you compile. Let's keep things a bit more minimal
 | and hide a few of those bits and pieces. Adjust as you wish.
 |
 */

module.exports.stats = {
    hash: false,
    version: false,
    timings: false,
    children: false,
    errors: false
};

process.noDeprecation = true;

module.exports.performance = { hints: false };

/*
 |--------------------------------------------------------------------------
 | Devtool
 |--------------------------------------------------------------------------
 |
 | Sourcemaps allow us to access our original source code within the
 | browser, even if we're serving a bundled script or stylesheet.
 | You may activate sourcemaps, by adding Mix.sourceMaps().
 |
 */

module.exports.devtool = Mix.sourcemaps;

/*
 |--------------------------------------------------------------------------
 | Webpack Dev Server Configuration
 |--------------------------------------------------------------------------
 |
 | If you want to use that flashy hot module replacement feature, then
 | we've got you covered. Here, we'll set some basic initial config
 | for the Node server. You very likely won't want to edit this.
 |
 */
module.exports.devServer = {
    historyApiFallback: true,
    noInfo: true,
    compress: true,
    quiet: true
};

/*
 |--------------------------------------------------------------------------
 | Plugins
 |--------------------------------------------------------------------------
 |
 | Lastly, we'll register a number of plugins to extend and configure
 | Webpack. To get you started, we've included a handful of useful
 | extensions, for versioning, OS notifications, and much more.
 |
 */

plugins.push(
    new webpack.ProvidePlugin(Mix.autoload || {}),

    new webpackPlugins.FriendlyErrorsWebpackPlugin({ clearConsole: Mix.options.clearConsole }),

    new webpackPlugins.StatsWriterPlugin({
        filename: 'mix-manifest.json',
        transform: Mix.manifest.transform.bind(Mix.manifest),
    }),

    new webpack.LoaderOptionsPlugin({
        minimize: Mix.inProduction,
        options: {
            postcss: Mix.options.postCss,
            context: __dirname,
            output: { path: './' }
        }
    })
);

if (Mix.browserSync) {
    plugins.push(
        new webpackPlugins.BrowserSyncPlugin(
            Object.assign({
                host: 'localhost',
                port: 3000,
                proxy: 'app.dev',
                files: [
                    'app/**/*.php',
                    'resources/views/**/*.php',
                    'public/js/**/*.js',
                    'public/css/**/*.css'
                ]
            }, Mix.browserSync),
            {
                reload: false
            }
        )
    );
}

if (Mix.options.notifications) {
    plugins.push(
        new webpackPlugins.WebpackNotifierPlugin({
            title: 'Laravel Mix',
            alwaysNotify: true,
            contentImage: Mix.Paths.root('node_modules/laravel-mix/icons/laravel.png')
        })
    );
}

if (Mix.copy) {
    Mix.copy.forEach(copy => {
        plugins.push(
            new webpackPlugins.CopyWebpackPlugin([copy])
        );
    });
}

if (Mix.extract) {
    plugins.push(
        new webpack.optimize.CommonsChunkPlugin({
            names: Mix.entryBuilder.extractions,
            minChunks: Infinity
        })
    );
}

if (Mix.options.versioning) {
    plugins.push(
        new webpack[Mix.inProduction ? 'HashedModuleIdsPlugin': 'NamedModulesPlugin'](),
        new webpackPlugins.WebpackChunkHashPlugin()
    );
}

if (Mix.options.purifyCss) {
    let PurifyCSSPlugin = require('purifycss-webpack');

    // By default, we'll scan all Blade and Vue files in our project.
    let paths = glob.sync(Mix.Paths.root('resources/views/**/*.blade.php')).concat(
        Mix.js.reduce((carry, js) => {
            return carry.concat(glob.sync(js.entry.map(entry => entry.base) + '/**/*.vue'));
        }, [])
    );

    plugins.push(new PurifyCSSPlugin(
        Object.assign({ paths }, Mix.options.purifyCss, { minimize: Mix.inProduction })
    ));
}

if (Mix.inProduction) {
    plugins.push(
        new webpack.DefinePlugin({
            'process.env': {
                NODE_ENV: '"production"'
            }
        })
    );

    if (Mix.options.uglify) {
        plugins.push(
            new webpack.optimize.UglifyJsPlugin(Mix.options.uglify)
        );
    }
}

plugins.push(
    new webpackPlugins.WebpackOnBuildPlugin(
        stats => Mix.events.fire('build', stats)
    )
);

module.exports.plugins = plugins;

/*
 |--------------------------------------------------------------------------
 | Mix Finalizing
 |--------------------------------------------------------------------------
 |
 | Now that we've declared the entirety of our Webpack configuration, the
 | final step is to scan for any custom configuration in the Mix file.
 | If mix.webpackConfig() is called, we'll merge it in, and build!
 |
 */

if (Mix.webpackConfig) {
    module.exports = require('webpack-merge').smart(
        module.exports, Mix.webpackConfig
    );
}
<|endoftext|>


<commit_before>import React from 'react';
import PropTypes from 'prop-types';
import { noop, isNil } from 'lodash';

import Label from '../Label';
import { LabelText, SelectBase } from '../BaseControls';
import {
  validationInputColor,
  validationTextColor
} from '../validationStateVars';

const optionsShape = {
  /** Text to display in drop down */
  optionText: PropTypes.string.isRequired,
  optionValue: PropTypes.string.isRequired
};

export default class Dropdown extends React.Component {
  static propTypes = {
    labelText: PropTypes.string.isRequired,
    /** The name of the select element*/
    name: PropTypes.string,
    /** Display label inline with dropdown */
    inline: PropTypes.bool,
    options: PropTypes.arrayOf(PropTypes.shape(optionsShape)),
    /** Display a default first option */
    includeDefaultFirstOption: PropTypes.bool,
    /** The text of the first option displayed */
    firstOptionDisplayText: PropTypes.string,
    /** The currently selected value */
    selectedValue: PropTypes.string,
    /** Display label and text with contextual state colorings */
    validationState: PropTypes.oneOf([
      'normal',
      'success',
      'warning',
      'danger'
    ]),
    /** Function to execute when the dropdown value changes */
    onOptionChanged: PropTypes.func,
    /** Function to execute when the dropdown loses focus */
    onDropdownFocusLost: PropTypes.func
  };

  static defaultProps = {
    inline: false,
    includeDefaultFirstOption: true,
    firstOptionDisplayText: '--',
    selectedValue: '',
    onOptionChanged: noop,
    onDropdownFocusLost: noop,
    validationState: 'normal'
  };

  constructor(props) {
    super(props);

    this.state = {
      currentValue: isNil(props.selectedValue) ? '' : props.selectedValue
    };

    this.handleOptionChanged = this.handleOptionChanged.bind(this);
    this.handleFocusLost = this.handleFocusLost.bind(this);
  }

  componentWillReceiveProps({ selectedValue }) {
    this.setState(() => ({
      currentValue: isNil(selectedValue) ? '' : selectedValue
    }));
  }

  handleEvent(event, handlerName) {
    const { value } = event.target;

    const handler = this.props[handlerName];
    this.setState({ currentValue: value }, () => handler(value));
  }

  handleOptionChanged(event) {
    this.handleEvent(event, 'onOptionChanged');
  }

  handleFocusLost(event) {
    this.handleEvent(event, 'onDropdownFocusLost');
  }

  render() {
    const {
      labelText,
      name,
      inline,
      options,
      includeDefaultFirstOption,
      firstOptionDisplayText,
      validationState,
      ...selectProps
    } = this.props;

    const { currentValue } = this.state;

    const firstOption = includeDefaultFirstOption ? (
      <option disabled value="">
        {firstOptionDisplayText}
      </option>
    ) : null;

    const selectOptions = options.map(opt => {
      const optionKey = opt.optionValue.replace(/\s/g, '');
      return (
        <option key={optionKey} value={opt.optionValue}>
          {opt.optionText}
        </option>
      );
    });

    return (
      <Label inline={inline}>
        <LabelText
          foregroundColor={validationTextColor[validationState]}
          inline={inline}
        >
          {labelText}
        </LabelText>
        <SelectBase
          name={name}
          value={currentValue}
          onChange={this.handleOptionChanged}
          onBlur={this.handleFocusLost}
          {...validationInputColor[validationState]}
          {...selectProps}
        >
          {firstOption}
          {selectOptions}
        </SelectBase>
      </Label>
    );
  }
}
<commit_msg>Allow the default first option to be selected<commit_after>import React from 'react';
import PropTypes from 'prop-types';
import { noop, isNil } from 'lodash';

import Label from '../Label';
import { LabelText, SelectBase } from '../BaseControls';
import {
  validationInputColor,
  validationTextColor
} from '../validationStateVars';

const optionsShape = {
  /** Text to display in drop down */
  optionText: PropTypes.string.isRequired,
  optionValue: PropTypes.string.isRequired
};

export default class Dropdown extends React.Component {
  static propTypes = {
    labelText: PropTypes.string.isRequired,
    /** The name of the select element*/
    name: PropTypes.string,
    /** Display label inline with dropdown */
    inline: PropTypes.bool,
    options: PropTypes.arrayOf(PropTypes.shape(optionsShape)),
    /** Display a default first option */
    includeDefaultFirstOption: PropTypes.bool,
    /** Prevent default first option from being selected */
    isDefaultFirstOptionDisabled: PropTypes.bool,
    /** The text of the first option displayed */
    firstOptionDisplayText: PropTypes.string,
    /** The currently selected value */
    selectedValue: PropTypes.string,
    /** Display label and text with contextual state colorings */
    validationState: PropTypes.oneOf([
      'normal',
      'success',
      'warning',
      'danger'
    ]),
    /** Function to execute when the dropdown value changes */
    onOptionChanged: PropTypes.func,
    /** Function to execute when the dropdown loses focus */
    onDropdownFocusLost: PropTypes.func
  };

  static defaultProps = {
    inline: false,
    includeDefaultFirstOption: true,
    isDefaultFirstOptionDisabled: true,
    firstOptionDisplayText: '--',
    selectedValue: '',
    onOptionChanged: noop,
    onDropdownFocusLost: noop,
    validationState: 'normal'
  };

  constructor(props) {
    super(props);

    this.state = {
      currentValue: isNil(props.selectedValue) ? '' : props.selectedValue
    };

    this.handleOptionChanged = this.handleOptionChanged.bind(this);
    this.handleFocusLost = this.handleFocusLost.bind(this);
  }

  componentWillReceiveProps({ selectedValue }) {
    this.setState(() => ({
      currentValue: isNil(selectedValue) ? '' : selectedValue
    }));
  }

  handleEvent(event, handlerName) {
    const { value } = event.target;

    const handler = this.props[handlerName];
    this.setState({ currentValue: value }, () => handler(value));
  }

  handleOptionChanged(event) {
    this.handleEvent(event, 'onOptionChanged');
  }

  handleFocusLost(event) {
    this.handleEvent(event, 'onDropdownFocusLost');
  }

  render() {
    const {
      labelText,
      name,
      inline,
      options,
      includeDefaultFirstOption,
      isDefaultFirstOptionDisabled,
      firstOptionDisplayText,
      validationState,
      ...selectProps
    } = this.props;

    const { currentValue } = this.state;

    const firstOption = includeDefaultFirstOption
      ? <option disabled={isDefaultFirstOptionDisabled} value="">
          {firstOptionDisplayText}
        </option>
      : null;

    const selectOptions = options.map(opt => {
      const optionKey = opt.optionValue.replace(/\s/g, '');
      return (
        <option key={optionKey} value={opt.optionValue}>
          {opt.optionText}
        </option>
      );
    });

    return (
      <Label inline={inline}>
        <LabelText
          foregroundColor={validationTextColor[validationState]}
          inline={inline}
        >
          {labelText}
        </LabelText>
        <SelectBase
          name={name}
          value={currentValue}
          onChange={this.handleOptionChanged}
          onBlur={this.handleFocusLost}
          {...validationInputColor[validationState]}
          {...selectProps}
        >
          {firstOption}
          {selectOptions}
        </SelectBase>
      </Label>
    );
  }
}
<|endoftext|>


<commit_before>define([
    './module',
    'jquery',
    'text!./word.html'
], function(directives, $, linkTpl) {
    'use strict';

    directives.directive('knovWord', ['$interval',
        function($interval) {
            function link(scope, element, attrs) {
                var timeoutId;
                var $link = $(element).find('a');

                function update() {
                    if ($link.offset().left < ($('body').width() / 2) ) {
                        $link.parent().addClass('hint--right');
                    } else {
                        $link.parent().addClass('hint--left');
                    }
                }

                scope.$watch(attrs.myCurrentTime, function(value) {
                    update();
                });

                element.on('$destroy', function() {
                    $interval.cancel(timeoutId);
                });

                // Hide link
                element.on('click', function(e) {
                    e.preventDefault();

                    if ($link.attr('data-link').length > 0) {
		                window.open($link.attr('data-link'), '_blank');
                    }

                    return false;
	            });

                timeoutId = $interval(function() {
                    update();
                }, 1000);
            }

            return {
                restrict: 'A',
                template: linkTpl,
                link: link
            };
        }
    ]);
});
<commit_msg>List update : adjust link's tooltip position<commit_after>define([
    './module',
    'jquery',
    'text!./word.html'
], function(directives, $, linkTpl) {
    'use strict';

    directives.directive('knovWord', ['$interval',
        function($interval) {
            function link(scope, element, attrs) {
                var timeoutId;
                var $link = $(element).find('a');

                function update() {
                // When the list is updated, adjust tooltip position
                    if ($link.offset().left < ($('body').width() / 2) ) {
                        $link.parent().addClass('hint--right');
                        $link.parent().removeClass('hint--left');
                    } else {
                        $link.parent().addClass('hint--left');
                        $link.parent().removeClass('hint--right');
                    }
                }

                scope.$watch(attrs.myCurrentTime, function(value) {
                    update();
                });

                element.on('$destroy', function() {
                    $interval.cancel(timeoutId);
                });

                // Hide link
                element.on('click', function(e) {
                    e.preventDefault();

                    if ($link.attr('data-link').length > 0) {
		                window.open($link.attr('data-link'), '_blank');
                    }

                    return false;
	            });

                timeoutId = $interval(function() {
                    update();
                }, 1000);
            }

            return {
                restrict: 'A',
                template: linkTpl,
                link: link
            };
        }
    ]);
});
<|endoftext|>


<commit_before>var mongoose = require('mongoose'),
    bug = require('./models/bug.js'),
    issue = require('./models/issue.js');

function REST_ROUTER(router, md5) {
    var self = this;
    self.handleRoutes(router, md5, self);
}

REST_ROUTER.prototype.handleRoutes= function(router, md5, self) {
    router.get("/",function(req, res){
        res.jsonp({
            "Message" : "Hello World below is my api :)",
            "GET requests": {
                "api/bug": "Returns all bugs",
                "api/bug/summary": "Returns all bugs with less data",
                "api/bug/id": "Returns a bug with a given id",
                "api/bug/id/summary": "Returns a bug with a given id and with less data",
                "api/issue": "Returns all issues",
                "api/issue/summary": "Returns all issues with less data",
                "api/issue/id": "Returns a issue with a given id",
                "api/issue/id/summary": "Returns a issue with a given id and with less data"
            },
            "POST requests": {
                "api/submitbug": {
                    "description": "Submits a bug to the web service and expects the following fields",
                    "fields": {
                        "exception": {
                            "description": "An exception thrown by the application, can be null",
                            "type": "String"
                        },
                        "dateTime": {
                            "description": "The date and time of submission",
                            "type": "Date"
                        },
                        "userDescription": {
                            "description": "A description the user reporting the bug can fill out",
                            "type": "String"
                        },
                        "progDescription": {
                            "description": "A description outputted by the program",
                            "type": "String"
                        },
                        "osName": {
                            "description": "The name of the operating system that the application was run on",
                            "type": "String"
                        },
                        "osVersion": {
                            "description": "The version of the operating system that the application was run on",
                            "type": "String"
                        },
                        "args": {
                            "description": "The arguments that the program was running with",
                            "type": "String"
                        },
                        "javaVersion": {
                            "description": "The version of the java that the applicaion was being run on",
                            "type": "String"
                        },
                        "histUndoPossible": {
                            "description": "If undo was possible",
                            "type": "Boolean"
                        },
                        "histRedoPossible": {
                            "description": "If redo was possible",
                            "type": "Boolean"
                        },
                        "navForwardPossible": {
                            "description": "If navigation forward was possible,",
                            "type": "String"
                        },
                        "navBackwardPossible": {
                            "description": "If navigation backwards was possible",
                            "type": "Boolean"
                        },

                        "screenshot": {
                            "description": "An image encoded in base64",
                            "type": "String"
                        },
                        "misc": {
                            "description": "Other data outputted from the application",
                            "type": "String"
                        }
                    }
                }
            }
        });
    });

    router.post("/submitbug", function(req, res) {
        var issueData = req.body;
        var bugSubmission = submitBug(issueData, md5, function (submission) {

            if (!submission.result) {
                //fixme: Note that passing the exact db error is bad in the real world as this can expose
                //internal implementation to hackers, for the purpose of debugging it has been included
                res.status(500).jsonp({"error" : true, "message" : "Error submitting bug", "dbError": submission.err});
                console.log("Something went wrong: " + submission.err);
            }
            else {
                res.jsonp({"error" : false, "message" : "Bug submitted!"});
            }
        }.bind(this));
    }.bind(self));

    router.get("/bug", function(req, res) {
        var query = bug.find();
        query.select('-__v -issues.__v');
        query.exec(function (err, result) {
            if (err) {
                res.status(500).jsonp({"error" : true, "message" : "error getting bugs", "dbError": err});
            }
            else {
                res.jsonp({"error" : false, "message" : "All the bugs", "data": result});
            }
        }.bind(this));
    }.bind(self));

    router.get("/bug/summary", function(req, res) {
        var query = bug.find();
        query.select('hash _id issues._id issues.dateTime issues.progDescription issues.userDescription');
        query.exec(function (err, result) {
            if (err) {
                res.status(500).jsonp({"error" : true, "message" : "error getting bugs", "dbError": err});
            }
            else {
                res.jsonp({"error" : false, "message" : "All the bugs", "data": result});
            }
        }.bind(this));
    }.bind(self));

    router.get("/bug/:id", function (req, res) {
        var id = req.params.id;
        if (id.length === 24) {
            var query = bug.findById(id, function (err, result) {
                query.select('-__v -issues.__v');
                if (err) {
                     res.status(500).jsonp({"error" : true, "message" : "error getting bug with id " + req.params.id, "dbError": err});
                }
                else if (result === null) {
                    res.status(404).jsonp({"error" : true, "message" : "Bug with id " + id + " was not found"});
                }
                else {
                    res.jsonp({"error" : false, "message" : "Found bug with id " + id, "data": result});
                }
            }.bind(this));
        }
        else {
            res.status(404).jsonp({"error" : true, "message" : "Invalid id"});
        }
    }.bind(self));

    router.get("/bug/:id/summary", function (req, res) {
        var id = req.params.id;
        if (id.length === 24) {
            var query = bug.findById(id, 'hash _id issues._id issues.dateTime issues.progDescription issues.userDescription', function (err, result) {
                if (err) {
                     res.status(500).jsonp({"error" : true, "message" : "error getting bug with id " + req.params.id, "dbError": err});
                }
                else if (result === null) {
                    res.status(404).jsonp({"error" : true, "message" : "Bug with id " + id + " was not found"});
                }
                else {
                    res.jsonp({"error" : false, "message" : "Found bug with id " + id, "data": result});
                }
            }.bind(this));
        }
        else {
            res.status(404).jsonp({"error" : true, "message" : "Invalid id"});
        }
    }.bind(self));

    router.get("/issue", function (req, res) {
        var query = issue.find();
        query.select('-__v');
        query.exec(function (err, result) {
            if (err) {
                res.status(500).jsonp({"error" : true, "message" : "error getting issues", "dbError": err});
            }
            else {
                res.jsonp({"error" : false, "message" : "All issues", "data": result});
            }
        }.bind(this));
    }.bind(self));

    router.get("/issue/summary", function (req, res) {
        var query = issue.find();
        query.select('_id dateTime progDescription userDescription');
        query.exec(function (err, result) {
            if (err) {
                res.status(500).jsonp({"error" : true, "message" : "error getting issues", "dbError": err});
            }
            else {
                res.jsonp({"error" : false, "message" : "All issues", "data": result});
            }
        }.bind(this));
    }.bind(self));

    router.get("/issue/:id", function (req, res) {
        var id = req.params.id;
        if (id.length === 24) {
            var query = issue.findById(id, '-__v', function (err, result) {
                if (err) {
                     res.status(500).jsonp({"error" : true, "message" : "error getting issue with id " + req.params.id, "dbError": err});
                }
                else if (result === null) {
                    res.status(404).jsonp({"error" : true, "message" : "Issue with id " + id + " was not found"});
                }
                else {
                    res.jsonp({"error" : false, "message" : "Found issue with id " + id, "data": result});
                }
            }.bind(this));
        }
        else {
            res.status(404).jsonp({"error" : true, "message" : "Invalid id"});
        }
    }.bind(self));

    router.get("/issue/:id/summary", function (req, res) {
        var id = req.params.id;
        if (id.length === 24) {
            var query = issue.findById(id, '_id dateTime progDescription userDescription', function (err, result) {
                if (err) {
                     res.status(500).jsonp({"error" : true, "message" : "error getting issue with id " + req.params.id, "dbError": err});
                }
                else if (result === null) {
                    res.status(404).jsonp({"error" : true, "message" : "Issue with id " + id + " was not found"});
                }
                else {
                    res.jsonp({"error" : false, "message" : "Found issue with id " + id, "data": result});
                }
            }.bind(this));
        }
        else {
            res.status(404).jsonp({"error" : true, "message" : "Invalid id"});
        }
    }.bind(self));

}

function submitBug(issueData, md5, callback) {
    var exceptionHash;
    if (issueData.exception === null) {
        exceptionHash = md5("noException");
    }
    else {
        exceptionHash = md5(issueData.exception);
    }

    var newIssue = new issue(issueData);
    newIssue.save(function (err) {
        if (err) callback(handleError(err));
    }.bind(this));

    // check to see if the issue is unique, if it is submit a new bug along with the issue
    // if not then update the bug record with the same hash with the new key.

    bug.findOneAndUpdate({hash: exceptionHash}, {$push: {issues: newIssue}}, {new: true, upsert: true}, function (err) {
        if (err) callback(handleError(err));
    }.bind(this));

    callback({result: true, err: ""});
}

function handleError(err) {
    console.log("Something went wrong: " + err);
    return {result: false, err: "something went wrong"};
}

module.exports = REST_ROUTER;<commit_msg>change summary part of api<commit_after>var mongoose = require('mongoose'),
    bug = require('./models/bug.js'),
    issue = require('./models/issue.js');

function REST_ROUTER(router, md5) {
    var self = this;
    self.handleRoutes(router, md5, self);
}

REST_ROUTER.prototype.handleRoutes= function(router, md5, self) {
    router.get("/",function(req, res){
        res.jsonp({
            "Message" : "Hello World below is my api :)",
            "GET requests": {
                "api/bug": "Returns all bugs",
                "api/bug/summary": "Returns all bugs with less data",
                "api/bug/id": "Returns a bug with a given id",
                "api/bug/id/summary": "Returns a bug with a given id and with less data",
                "api/issue": "Returns all issues",
                "api/issue/summary": "Returns all issues with less data",
                "api/issue/id": "Returns a issue with a given id",
                "api/issue/id/summary": "Returns a issue with a given id and with less data"
            },
            "POST requests": {
                "api/submitbug": {
                    "description": "Submits a bug to the web service and expects the following fields",
                    "fields": {
                        "exception": {
                            "description": "An exception thrown by the application, can be null",
                            "type": "String"
                        },
                        "dateTime": {
                            "description": "The date and time of submission",
                            "type": "Date"
                        },
                        "userDescription": {
                            "description": "A description the user reporting the bug can fill out",
                            "type": "String"
                        },
                        "progDescription": {
                            "description": "A description outputted by the program",
                            "type": "String"
                        },
                        "osName": {
                            "description": "The name of the operating system that the application was run on",
                            "type": "String"
                        },
                        "osVersion": {
                            "description": "The version of the operating system that the application was run on",
                            "type": "String"
                        },
                        "args": {
                            "description": "The arguments that the program was running with",
                            "type": "String"
                        },
                        "javaVersion": {
                            "description": "The version of the java that the applicaion was being run on",
                            "type": "String"
                        },
                        "histUndoPossible": {
                            "description": "If undo was possible",
                            "type": "Boolean"
                        },
                        "histRedoPossible": {
                            "description": "If redo was possible",
                            "type": "Boolean"
                        },
                        "navForwardPossible": {
                            "description": "If navigation forward was possible,",
                            "type": "String"
                        },
                        "navBackwardPossible": {
                            "description": "If navigation backwards was possible",
                            "type": "Boolean"
                        },

                        "screenshot": {
                            "description": "An image encoded in base64",
                            "type": "String"
                        },
                        "misc": {
                            "description": "Other data outputted from the application",
                            "type": "String"
                        }
                    }
                }
            }
        });
    });

    router.post("/submitbug", function(req, res) {
        var issueData = req.body;
        var bugSubmission = submitBug(issueData, md5, function (submission) {

            if (!submission.result) {
                //fixme: Note that passing the exact db error is bad in the real world as this can expose
                //internal implementation to hackers, for the purpose of debugging it has been included
                res.status(500).jsonp({"error" : true, "message" : "Error submitting bug", "dbError": submission.err});
                console.log("Something went wrong: " + submission.err);
            }
            else {
                res.jsonp({"error" : false, "message" : "Bug submitted!"});
            }
        }.bind(this));
    }.bind(self));

    router.get("/bug", function(req, res) {
        var query = bug.find();
        query.select('-__v -issues.__v');
        query.exec(function (err, result) {
            if (err) {
                res.status(500).jsonp({"error" : true, "message" : "error getting bugs", "dbError": err});
            }
            else {
                res.jsonp({"error" : false, "message" : "All the bugs", "data": result});
            }
        }.bind(this));
    }.bind(self));

    router.get("/bug/summary", function(req, res) {
        var query = bug.find();
        query.select('hash ' +
        '_id ' +
        'issues._id issues.dateTime ' +
        'issues.progDescription ' +
        'issues.userDescription ' +
        'issues.histRedoPossible ' +
        'issues.histUndoPossible ' +
        'issues.navBackwardPossible ' +
        'issues.navForwardPossible');
        query.exec(function (err, result) {
            if (err) {
                res.status(500).jsonp({"error" : true, "message" : "error getting bugs", "dbError": err});
            }
            else {
                res.jsonp({"error" : false, "message" : "All the bugs", "data": result});
            }
        }.bind(this));
    }.bind(self));

    router.get("/bug/:id", function (req, res) {
        var id = req.params.id;
        if (id.length === 24) {
            var query = bug.findById(id, function (err, result) {
                query.select('-__v -issues.__v');
                if (err) {
                     res.status(500).jsonp({"error" : true, "message" : "error getting bug with id " + req.params.id, "dbError": err});
                }
                else if (result === null) {
                    res.status(404).jsonp({"error" : true, "message" : "Bug with id " + id + " was not found"});
                }
                else {
                    res.jsonp({"error" : false, "message" : "Found bug with id " + id, "data": result});
                }
            }.bind(this));
        }
        else {
            res.status(404).jsonp({"error" : true, "message" : "Invalid id"});
        }
    }.bind(self));

    router.get("/bug/:id/summary", function (req, res) {
        var id = req.params.id;
        if (id.length === 24) {
            var query = bug.findById(id,
                'hash ' +
                '_id ' +
                'issues._id issues.dateTime ' +
                'issues.progDescription ' +
                'issues.userDescription ' +
                'issues.histRedoPossible ' +
                'issues.histUndoPossible ' +
                'issues.navBackwardPossible ' +
                'issues.navForwardPossible', function (err, result) {
                if (err) {
                     res.status(500).jsonp({"error" : true, "message" : "error getting bug with id " + req.params.id, "dbError": err});
                }
                else if (result === null) {
                    res.status(404).jsonp({"error" : true, "message" : "Bug with id " + id + " was not found"});
                }
                else {
                    res.jsonp({"error" : false, "message" : "Found bug with id " + id, "data": result});
                }
            }.bind(this));
        }
        else {
            res.status(404).jsonp({"error" : true, "message" : "Invalid id"});
        }
    }.bind(self));

    router.get("/issue", function (req, res) {
        var query = issue.find();
        query.select('-__v');
        query.exec(function (err, result) {
            if (err) {
                res.status(500).jsonp({"error" : true, "message" : "error getting issues", "dbError": err});
            }
            else {
                res.jsonp({"error" : false, "message" : "All issues", "data": result});
            }
        }.bind(this));
    }.bind(self));

    router.get("/issue/summary", function (req, res) {
        var query = issue.find();
        query.select('_id ' +
        'dateTime ' +
        'progDescription ' +
        'userDescription ' +
        'histRedoPossible ' +
        'histUndoPossible ' +
        'navBackwardPossible ' +
        'navForwardPossible');
        query.exec(function (err, result) {
            if (err) {
                res.status(500).jsonp({"error" : true, "message" : "error getting issues", "dbError": err});
            }
            else {
                res.jsonp({"error" : false, "message" : "All issues", "data": result});
            }
        }.bind(this));
    }.bind(self));

    router.get("/issue/:id", function (req, res) {
        var id = req.params.id;
        if (id.length === 24) {
            var query = issue.findById(id, '-__v', function (err, result) {
                if (err) {
                     res.status(500).jsonp({"error" : true, "message" : "error getting issue with id " + req.params.id, "dbError": err});
                }
                else if (result === null) {
                    res.status(404).jsonp({"error" : true, "message" : "Issue with id " + id + " was not found"});
                }
                else {
                    res.jsonp({"error" : false, "message" : "Found issue with id " + id, "data": result});
                }
            }.bind(this));
        }
        else {
            res.status(404).jsonp({"error" : true, "message" : "Invalid id"});
        }
    }.bind(self));

    router.get("/issue/:id/summary", function (req, res) {
        var id = req.params.id;
        if (id.length === 24) {
            var query = issue.findById(id, '_id ' +
            'dateTime ' +
            'progDescription ' +
            'userDescription ' +
            'histRedoPossible ' +
            'histUndoPossible ' +
            'navBackwardPossible ' +
            'navForwardPossible', function (err, result) {
                if (err) {
                     res.status(500).jsonp({"error" : true, "message" : "error getting issue with id " + req.params.id, "dbError": err});
                }
                else if (result === null) {
                    res.status(404).jsonp({"error" : true, "message" : "Issue with id " + id + " was not found"});
                }
                else {
                    res.jsonp({"error" : false, "message" : "Found issue with id " + id, "data": result});
                }
            }.bind(this));
        }
        else {
            res.status(404).jsonp({"error" : true, "message" : "Invalid id"});
        }
    }.bind(self));

}

function submitBug(issueData, md5, callback) {
    var exceptionHash;
    if (issueData.exception === null) {
        exceptionHash = md5("noException");
    }
    else {
        exceptionHash = md5(issueData.exception);
    }

    var newIssue = new issue(issueData);
    newIssue.save(function (err) {
        if (err) callback(handleError(err));
    }.bind(this));

    // check to see if the issue is unique, if it is submit a new bug along with the issue
    // if not then update the bug record with the same hash with the new key.

    bug.findOneAndUpdate({hash: exceptionHash}, {$push: {issues: newIssue}}, {new: true, upsert: true}, function (err) {
        if (err) callback(handleError(err));
    }.bind(this));

    callback({result: true, err: ""});
}

function handleError(err) {
    console.log("Something went wrong: " + err);
    return {result: false, err: "something went wrong"};
}

module.exports = REST_ROUTER;<|endoftext|>


<commit_before>var x11  = require('x11');
var exec = require('child_process').exec;

// Load the objects from objects.js
var Workspaces = require('./objects').Workspaces,
    Workspace  = require('./objects').Workspace,
    Screen     = require('./objects').Screen,
    Window     = require('./objects').Window,
    Container  = require('./objects').Container;

// The workspaces currently available
var workspaces;

// The available key shortcuts that are known
var key_combinations = require("./keys");

x11.createClient(function(err, display) {
	// Set the connection to the X server in global namespace
	// as a hack since almost every file uses it
	global.X = display.client;

	// Create the workspaces object
	workspaces = new Workspaces( display.screen );

	// By adding the substructure redirect you become the window manager.
	// TODO Should we register for all screens?
	global.X.ChangeWindowAttributes(
		display.screen[0].root,
		{
			// node-x11/lib/eventmask.js
			// https://github.com/sidorares/node-x11/blob/master/lib/eventmask.js
			// Comment non-required events
			eventMask:  x11.eventMask.KeyPress             |
			            x11.eventMask.KeyRelease           |
			            x11.eventMask.ButtonPress          |
			            x11.eventMask.ButtonRelease        |
			            x11.eventMask.EnterWindow          |
			            x11.eventMask.LeaveWindow          |  // Event Type: 8
			            x11.eventMask.PointerMotion        |
			            x11.eventMask.PointerMotionHint    |
			            x11.eventMask.Button1Motion        |
			            x11.eventMask.Button2Motion        |
			            x11.eventMask.Button3Motion        |
			            x11.eventMask.Button4Motion        |
			            x11.eventMask.Button5Motion        |
			            x11.eventMask.ButtonMotion         |
			            x11.eventMask.KeymapState          | // Event Type: 11
			            x11.eventMask.Exposure             |
			            x11.eventMask.VisibilityChange     |
			            x11.eventMask.StructureNotify      |
			            x11.eventMask.ResizeRedirect       |
			            x11.eventMask.SubstructureNotify   |
			            x11.eventMask.SubstructureRedirect |
			            x11.eventMask.FocusChange          |
			            x11.eventMask.PropertyChange       |
			            x11.eventMask.ColormapChange       |
			            x11.eventMask.OwnerGrabButton
		},
		function(err) {
			if( err.error === 10 ) {
				console.error( "Another window manager is already running" );
			}
			console.error(err);
			process.exit(1);
		}
	);

	// Grab all key combinations which are specified in the configuration file.
	key_combinations.forEach(function(keyConfiguration){
		global.X.GrabKey(display.screen[0].root, 0, translateModifiers(keyConfiguration.modifier),
				keyConfiguration.key, 0, 1);
	});

	// Load the programs that should get started
	// and start them
	var programs = require("./startup");
	programs.forEach(function(curr,ind,arr) { exec(curr) });
}).on('error', function(err) {
	console.error(err);
}).on('event', function(ev) {
	//console.log(ev);
	if( ev.name === "MapRequest" ) {
		workspaces.getCurrentWorkspace().addWindow( ev.wid );
	} else if ( ev.name === "DestroyNotify" ) {
		// Just search through all windows and remove the window
		// that got destroyed out of the tree.
		workspaces.forEachWindow(function(window) {
			if( window.window_id === ev.wid ) {
				window.remove();
			}
		});
	} else if ( ev.name === "ConfigureRequest" ) {
		// Don't allow them window to resize, we decide
		// how large the window is going to be!
		//X.ResizeWindow(ev.wid, ev.width, ev.height);
	} else if ( ev.name === "KeyPress" ) {
		// Go through all configured key combinations.
		for(var binding_index in key_combinations){
			var binding =  key_combinations[binding_index];
			// Check if this is the binding which we are seeking.
			if(binding.key === ev.keycode){
				if(translateModifiers(binding.modifier) === (ev.buttons&translateModifiers(binding.modifier))){
					if(binding.hasOwnProperty('command')){
						console.log("Launching airwm-command: '", binding.command, "'.");
						switch(binding.command){
							case "Shutdown":
								process.exit(0);
								break;
							case "CloseWindow":
								console.log("Closing window...", ev.child);
								workspaces.getCurrentWorkspace().removeWindow( ev.child );
								break;
							case "SwitchTilingMode":
								console.log("Switching tiling mode");
								workspaces.getCurrentWorkspace().switchTilingMode();
								break;
							default:
								break;
						}
					} else if(binding.hasOwnProperty("program")){
						console.log("Launching external application: '", binding.program, "'.");
						exec( binding.program );
					}
				}
			}
		}
	} else if ( ev.name === "KeyRelease" ) {
	}
});

translateModifiers = function(sModifier){
	switch(sModifier){
		case "super":
			return 64;
		default:
			return 0;
	}
}

<commit_msg>For var ... in ... to ; ; for loop.<commit_after>var x11  = require('x11');
var exec = require('child_process').exec;

// Load the objects from objects.js
var Workspaces = require('./objects').Workspaces,
    Workspace  = require('./objects').Workspace,
    Screen     = require('./objects').Screen,
    Window     = require('./objects').Window,
    Container  = require('./objects').Container;

// The workspaces currently available
var workspaces;

// The available key shortcuts that are known
var key_combinations = require("./keys");

x11.createClient(function(err, display) {
	// Set the connection to the X server in global namespace
	// as a hack since almost every file uses it
	global.X = display.client;

	// Create the workspaces object
	workspaces = new Workspaces( display.screen );

	// By adding the substructure redirect you become the window manager.
	// TODO Should we register for all screens?
	global.X.ChangeWindowAttributes(
		display.screen[0].root,
		{
			// node-x11/lib/eventmask.js
			// https://github.com/sidorares/node-x11/blob/master/lib/eventmask.js
			// Comment non-required events
			eventMask:  x11.eventMask.KeyPress             |
			            x11.eventMask.KeyRelease           |
			            x11.eventMask.ButtonPress          |
			            x11.eventMask.ButtonRelease        |
			            x11.eventMask.EnterWindow          |
			            x11.eventMask.LeaveWindow          |  // Event Type: 8
			            x11.eventMask.PointerMotion        |
			            x11.eventMask.PointerMotionHint    |
			            x11.eventMask.Button1Motion        |
			            x11.eventMask.Button2Motion        |
			            x11.eventMask.Button3Motion        |
			            x11.eventMask.Button4Motion        |
			            x11.eventMask.Button5Motion        |
			            x11.eventMask.ButtonMotion         |
			            x11.eventMask.KeymapState          | // Event Type: 11
			            x11.eventMask.Exposure             |
			            x11.eventMask.VisibilityChange     |
			            x11.eventMask.StructureNotify      |
			            x11.eventMask.ResizeRedirect       |
			            x11.eventMask.SubstructureNotify   |
			            x11.eventMask.SubstructureRedirect |
			            x11.eventMask.FocusChange          |
			            x11.eventMask.PropertyChange       |
			            x11.eventMask.ColormapChange       |
			            x11.eventMask.OwnerGrabButton
		},
		function(err) {
			if( err.error === 10 ) {
				console.error( "Another window manager is already running" );
			}
			console.error(err);
			process.exit(1);
		}
	);

	// Grab all key combinations which are specified in the configuration file.
	key_combinations.forEach(function(keyConfiguration){
		global.X.GrabKey(display.screen[0].root, 0, translateModifiers(keyConfiguration.modifier),
				keyConfiguration.key, 0, 1);
	});

	// Load the programs that should get started
	// and start them
	var programs = require("./startup");
	programs.forEach(function(curr,ind,arr) { exec(curr) });
}).on('error', function(err) {
	console.error(err);
}).on('event', function(ev) {
	//console.log(ev);
	if( ev.name === "MapRequest" ) {
		workspaces.getCurrentWorkspace().addWindow( ev.wid );
	} else if ( ev.name === "DestroyNotify" ) {
		// Just search through all windows and remove the window
		// that got destroyed out of the tree.
		workspaces.forEachWindow(function(window) {
			if( window.window_id === ev.wid ) {
				window.remove();
			}
		});
	} else if ( ev.name === "ConfigureRequest" ) {
		// Don't allow them window to resize, we decide
		// how large the window is going to be!
		//X.ResizeWindow(ev.wid, ev.width, ev.height);
	} else if ( ev.name === "KeyPress" ) {
		// Go through all configured key combinations.
		for(var i = 0; i < key_combinations.length; ++i){
			var binding =  key_combinations[i];
			// Check if this is the binding which we are seeking.
			if(binding.key === ev.keycode){
				if(translateModifiers(binding.modifier) === (ev.buttons&translateModifiers(binding.modifier))){
					if(binding.hasOwnProperty('command')){
						console.log("Launching airwm-command: '", binding.command, "'.");
						switch(binding.command){
							case "Shutdown":
								process.exit(0);
								break;
							case "CloseWindow":
								console.log("Closing window...", ev.child);
								workspaces.getCurrentWorkspace().removeWindow( ev.child );
								break;
							case "SwitchTilingMode":
								console.log("Switching tiling mode");
								workspaces.getCurrentWorkspace().switchTilingMode();
								break;
							default:
								break;
						}
					} else if(binding.hasOwnProperty("program")){
						console.log("Launching external application: '", binding.program, "'.");
						exec( binding.program );
					}
				}
			}
		}
	} else if ( ev.name === "KeyRelease" ) {
	}
});

translateModifiers = function(sModifier){
	switch(sModifier){
		case "super":
			return 64;
		default:
			return 0;
	}
}

<|endoftext|>


<commit_before>
function get_thumb_of(name) {
	if (name.match(".avi"))
		return name.replace(".avi", ".thm");
	if (name.match(".AVI"))
		return name.replace(".AVI", ".THM");
	return name;
}

var hash = null;

function anchor() {
	var anchor;

	if (hash != document.location.hash) {
		// store complete hash including #
		hash = document.location.hash;
		// but strip # for anchor part to pass to select()
		anchor = hash.substring(1);
		// when opening from the index, assume no anchor
		if (hash == "")
			anchor = "all"; //entries[0];
	} else {
		anchor = "all"; //entries[0];
	}

	return anchor;
}

function select(entry) {
	var selected = 0;

	for (count = 0; count < entries.length; count++)
		if (entry == entries[count])
			selected = count;

	// are we looking at an album index?
	if (entry == "all") {
		var thumbs = "
\n";
		// paint all the thumbnails
		for (count = 0; count < entries.length; count++) {
			var thumbnailimage = get_thumb_of(entries[count]);
			if ((count % 5) == 0)
				thumbs += "

\n";
			thumbs += "
";
// doesn't work because backrefs are broken atm
// thumbs += "
";
			thumbs += " \n
\n";
		}
		thumbs += "
\n";

		// Finished constructing the thumbs div
		document.getElementById('thumbs').innerHTML = thumbs;
		document.selected = -1;
		return;
	}

	// determine the range over 9 images to show
	var start = Math.max(selected - 4, 0);
	start = Math.min(start, Math.max(0, entries.length - 9));
	var stop = Math.min(start + 9, entries.length);

	// links to previous 9 images in the thumbs index
	var thumbs = "";
	if (start > 0) {
		var center = Math.max(selected - 9, 0);
		thumbs += "\n";
	}

	// show images start -> stop and put "entry" in display box
	for (count = start; count < stop; count++) {
		// thumbnail this
		var thumbnailimage = get_thumb_of(entries[count]);
		thumbs += "<div style=\"display: inline-block; ";
		if (Math.abs(selected - count) <= 1) {
			thumbs += "width: 120px; \">";
		} else {
			thumbs += "width: 60px; \">";
		}
		thumbs += "<img style=\"vertical-align: text-top;\" ";
		if (selected == count) {
			thumbs += "class=\"selected\" ";
		}
		if (Math.abs(selected - count) <= 1) {
			thumbs += "src=\"/image.php?r=1&x=100&y=100&i=" + album + "/" + thumbnailimage + "\" /> ";
		} else {
			thumbs += "src=\"/image.php?r=1&x=50&y=50&i=" + album + "/" + thumbnailimage + "\" /> ";
		}
		thumbs += "
\n";
	}

	// fill preload div
	var preload = "";
	if (stop < entries.length) {
		var thumbnailimage = get_thumb_of(entries[stop]);
		preload += "\n";
	}

	if (selected + 2 < entries.length) {
		var thumbnailimage = get_thumb_of(entries[selected + 2]);
		preload += "\n";
	}

	if ((selected + 1) < entries.length) {
		if (!(entry.match(".avi") || entry.match(".AVI"))) {
			preload += "\n";
		}
	}
	document.getElementById('preload').innerHTML = preload;

	// links to next 9 images in the thumbs index
	if (stop < entries.length) {
		var center = Math.min(stop + 5, entries.length)
		thumbs += "\n";
	}
	// finish of thumbs with a clear: both;
	thumbs += "

\n";

	// Finished constructing the thumbs div
	document.getElementById('thumbs').innerHTML = thumbs;

	var content = "\n";

	// construct the map
	content += "<map name=\"map-" + entry + "\">\n";
	if (selected > 0) {
		content += "<area shape=\"rect\" coords=\"0,0,250,800\" href=\"javascript: select('" + entries[selected - 1] + "')\" />\n";
	}
	if (selected < (entries.length - 1)) {
		content += "<area shape=\"rect\" coords=\"400,0,800,800\" href=\"javascript: select('" + entries[selected + 1] + "')\" />\n";
	}
	content += "</map>\n";

	if (selected > 0) {
		content += "\n";
	}

	// display selected image
	if (entry.match(".avi") || entry.match(".AVI")) {
		// Video display
		content += "<embed autoplay=\"true\" autostart=\"true\" uimode=\"true\" type=\"application/x-mplayer2\" id=\"MediaPlayer\" src=\"/" + album + "/" + entry + "\" style=\"visibility: visible;\" height=\"480\" width=\"640\" pluginspage=\"http://www.microsoft.com/windows/windowsmedia/download/\">\n";
	} else {
		// image display
		content += "\n";
	}

	if (selected + 1 < entries.length)
		content += "\n";

	content += "
\n" + album + " / " + "" + entry + "\n";

	// and display
	document.getElementById('content').innerHTML = content;
	document.location.hash = entry;
	document.selected = selected;
}

function keypressed(e) {
	e = e || window.event;

	var k = e.keyCode || e.which;

	switch(k) {
	case 78: //left
	case 32: // space
	case 39: // right
		if (document.selected < entries.length - 1)
			select(entries[document.selected + 1]);
		break;
	case 80: // p
	case 8:  // backspace
	case 37: // left
		if (document.selected > 0)
			select(entries[document.selected - 1]);
		break;
	case 38: // up
		select("all");
		break;
	case 40: // down
		if (document.selected > 0)
			select(entries[document.selected]);
		break;
	default:
		//alert(k);
		break;
	}

	return true;
}

document.onkeydown = keypressed;

<commit_msg>Revert "Space thumbnails equally a bit more..."<commit_after>
function get_thumb_of(name) {
	if (name.match(".avi"))
		return name.replace(".avi", ".thm");
	if (name.match(".AVI"))
		return name.replace(".AVI", ".THM");
	return name;
}

var hash = null;

function anchor() {
	var anchor;

	if (hash != document.location.hash) {
		// store complete hash including #
		hash = document.location.hash;
		// but strip # for anchor part to pass to select()
		anchor = hash.substring(1);
		// when opening from the index, assume no anchor
		if (hash == "")
			anchor = "all"; //entries[0];
	} else {
		anchor = "all"; //entries[0];
	}

	return anchor;
}

function select(entry) {
	var selected = 0;

	for (count = 0; count < entries.length; count++)
		if (entry == entries[count])
			selected = count;

	// are we looking at an album index?
	if (entry == "all") {
		var thumbs = "
\n";
		// paint all the thumbnails
		for (count = 0; count < entries.length; count++) {
			var thumbnailimage = get_thumb_of(entries[count]);
			if ((count % 5) == 0)
				thumbs += "

\n";
			thumbs += "
";
// doesn't work because backrefs are broken atm
// thumbs += "
";
			thumbs += " \n
\n";
		}
		thumbs += "
\n";

		// Finished constructing the thumbs div
		document.getElementById('thumbs').innerHTML = thumbs;
		document.selected = -1;
		return;
	}

	// determine the range over 9 images to show
	var start = Math.max(selected - 4, 0);
	start = Math.min(start, Math.max(0, entries.length - 9));
	var stop = Math.min(start + 9, entries.length);

	// links to previous 9 images in the thumbs index
	var thumbs = "";
	if (start > 0) {
		var center = Math.max(selected - 9, 0);
		thumbs += "\n";
	}

	// show images start -> stop and put "entry" in display box
	for (count = start; count < stop; count++) {
		// thumbnail this
		var thumbnailimage = get_thumb_of(entries[count]);
		thumbs += "<img style=\"vertical-align: text-top;\" ";
		if (selected == count) {
			thumbs += "class=\"selected\" ";
		}
		if (Math.abs(selected - count) <= 1) {
			thumbs += "src=\"/image.php?r=1&x=100&y=100&i=" + album + "/" + thumbnailimage + "\" /> \n";
		} else {
			thumbs += "src=\"/image.php?r=1&x=50&y=50&i=" + album + "/" + thumbnailimage + "\" /> \n";
		}
	}

	// fill preload div
	var preload = "";
	if (stop < entries.length) {
		var thumbnailimage = get_thumb_of(entries[stop]);
		preload += "\n";
	}

	if (selected + 2 < entries.length) {
		var thumbnailimage = get_thumb_of(entries[selected + 2]);
		preload += "\n";
	}

	if ((selected + 1) < entries.length) {
		if (!(entry.match(".avi") || entry.match(".AVI"))) {
			preload += "\n";
		}
	}
	document.getElementById('preload').innerHTML = preload;

	// links to next 9 images in the thumbs index
	if (stop < entries.length) {
		var center = Math.min(stop + 5, entries.length)
		thumbs += "\n";
	}

	// Finished constructing the thumbs div
	document.getElementById('thumbs').innerHTML = thumbs;

	var content = "\n";

	// construct the map
	content += "<map name=\"map-" + entry + "\">\n";
	if (selected > 0) {
		content += "<area shape=\"rect\" coords=\"0,0,250,800\" href=\"javascript: select('" + entries[selected - 1] + "')\" />\n";
	}
	if (selected < (entries.length - 1)) {
		content += "<area shape=\"rect\" coords=\"400,0,800,800\" href=\"javascript: select('" + entries[selected + 1] + "')\" />\n";
	}
	content += "</map>\n";

	if (selected > 0) {
		content += "\n";
	}

	// display selected image
	if (entry.match(".avi") || entry.match(".AVI")) {
		// Video display
		content += "<embed autoplay=\"true\" autostart=\"true\" uimode=\"true\" type=\"application/x-mplayer2\" id=\"MediaPlayer\" src=\"/" + album + "/" + entry + "\" style=\"visibility: visible;\" height=\"480\" width=\"640\" pluginspage=\"http://www.microsoft.com/windows/windowsmedia/download/\">\n";
	} else {
		// image display
		content += "\n";
	}

	if (selected + 1 < entries.length)
		content += "\n";

	content += "
\n" + album + " / " + "" + entry + "\n";

	// and display
	document.getElementById('content').innerHTML = content;
	document.location.hash = entry;
	document.selected = selected;
}

function keypressed(e) {
	e = e || window.event;

	var k = e.keyCode || e.which;

	switch(k) {
	case 78: //left
	case 32: // space
	case 39: // right
		if (document.selected < entries.length - 1)
			select(entries[document.selected + 1]);
		break;
	case 80: // p
	case 8:  // backspace
	case 37: // left
		if (document.selected > 0)
			select(entries[document.selected - 1]);
		break;
	case 38: // up
		select("all");
		break;
	case 40: // down
		if (document.selected > 0)
			select(entries[document.selected]);
		break;
	default:
		//alert(k);
		break;
	}

	return true;
}

document.onkeydown = keypressed;

<|endoftext|>


<commit_before>
const EXPORT = ['Migration'];
/*
 * バージョンによってのコンフィグの差異を変更する
 */

var Migration = {
    // 現在の conf のバージョン
    CURRENT_VERSION: 2,

    migration: function() {
        let currentVer = Prefs.bookmark.get('migration.version') || 0;
        let migrations = Migration.Migrations;
        for (let i = 0,len = migrations.length;  i < len; i++) {
            if (currentVer < i+1) {
                let m = migrations[i];
                p('execute migration: ' + m.name);
                m();
                Prefs.bookmark.set('migration.version', i + 1);
            }
        }
    },
}

EventService.createListener('Migration', function() {
    Migration.migration();
});

Migration.Migrations = [
    // デバッグログに、Migration の無名関数の名前を表示するので、つけておく
    function M_1_toolbarMenuInstall() {
        // やっぱり標準ではインストールしない
        return;
        var toolbar = document.getElementById('nav-bar');
        try {
            // Fx 3.0 unified-back-forward-button,reload-button,stop-button,home-button,
            // hBookmark-toolbar-home,quickrestart-button,urlbar-container,search-container
            let bars = toolbar.currentSet.split(',');
            bars = bars.filter(function(n) n.indexOf('hBookmark-toolbar-' == -1));

            let lastButton = null;
            let flag = false;
            let newSet = [];

            for (let i = 0;  i < bars.length; i++) {
                let name = bars[i];
                let el = document.getElementById(name);
                if (flag) {
                    //
                } else if (el && name.indexOf('-button') >= 0 ) {
                    lastButton = el;
                } else if (lastButton) {
                    // -button という ID が無くなった直後に追加
                    newSet.push('hBookmark-toolbar-add-button');
                    newSet.push('hBookmark-toolbar-home-button');
                    // newSet.push('hBookmark-toolbar-dropdown');
                    flag = true;
                }
                newSet.push(name);
            }
            if (flag) {
                newSet = newSet.join(',');
                toolbar.currentSet = newSet;
                toolbar.setAttribute('currentset', newSet);
                document.getElementById('navigator-toolbox').ownerDocument.persist(toolbar.id, 'currentset');
                BrowserToolboxCustomizeDone(true);
            }
        } catch(e) {
            p('install fail!: ' + e.toString());
        }
    },
    function M_2_openStartPage() {
        // 初回インストール時に、start ページを表示する
        openUILinkIn('http://b.hatena.ne.jp/guide/firefox_start', 'tab');
    },
];

<commit_msg>ロードタイミング変更<commit_after>
const EXPORT = ['Migration'];
/*
 * バージョンによってのコンフィグの差異を変更する
 */

var Migration = {
    // 現在の conf のバージョン
    CURRENT_VERSION: 2,

    migration: function() {
        let currentVer = Prefs.bookmark.get('migration.version') || 0;
        let migrations = Migration.Migrations;
        for (let i = 0,len = migrations.length;  i < len; i++) {
            if (currentVer < i+1) {
                let m = migrations[i];
                p('execute migration: ' + m.name);
                m();
                Prefs.bookmark.set('migration.version', i + 1);
            }
        }
    },
}

EventService.createListener('Migration', function() {
    Migration.migration();
});

Migration.Migrations = [
    // デバッグログに、Migration の無名関数の名前を表示するので、つけておく
    function M_1_toolbarMenuInstall() {
        // やっぱり標準ではインストールしない
        return;
        var toolbar = document.getElementById('nav-bar');
        try {
            // Fx 3.0 unified-back-forward-button,reload-button,stop-button,home-button,
            // hBookmark-toolbar-home,quickrestart-button,urlbar-container,search-container
            let bars = toolbar.currentSet.split(',');
            bars = bars.filter(function(n) n.indexOf('hBookmark-toolbar-' == -1));

            let lastButton = null;
            let flag = false;
            let newSet = [];

            for (let i = 0;  i < bars.length; i++) {
                let name = bars[i];
                let el = document.getElementById(name);
                if (flag) {
                    //
                } else if (el && name.indexOf('-button') >= 0 ) {
                    lastButton = el;
                } else if (lastButton) {
                    // -button という ID が無くなった直後に追加
                    newSet.push('hBookmark-toolbar-add-button');
                    newSet.push('hBookmark-toolbar-home-button');
                    // newSet.push('hBookmark-toolbar-dropdown');
                    flag = true;
                }
                newSet.push(name);
            }
            if (flag) {
                newSet = newSet.join(',');
                toolbar.currentSet = newSet;
                toolbar.setAttribute('currentset', newSet);
                document.getElementById('navigator-toolbox').ownerDocument.persist(toolbar.id, 'currentset');
                BrowserToolboxCustomizeDone(true);
            }
        } catch(e) {
            p('install fail!: ' + e.toString());
        }
    },
    function M_2_openStartPage() {
        // 初回インストール時に、start ページを表示する
        EventService.createListener('load', function() {
            setTimeout(function() {
                p('open start page');
                openUILinkIn('http://b.hatena.ne.jp/guide/firefox_start', 'tab');
            }, 1000);
        });

    },
];

<|endoftext|>


<commit_before><commit_msg>delete unused file handlers.js<commit_after><|endoftext|>


<commit_before>import {api} from '../api';
import AuthService from './AuthService';
const angular = require('angular');

module.exports = 'billett.auth';

(function() {
    'use strict';

    var module = angular.module('billett.auth', [
        'ui.router'
    ]);

    module.config(function($stateProvider) {
        $stateProvider.state('login', {
            url: '/login',
            template: 'Går til logg inn side',
            controller: function($location) {
                window.location.href = api('login?url=' + encodeURIComponent($location.path()));
            }
        }).
        state('logout', {
            url: '/logout',
            template: 'Logger ut',
            controller: function() {
                window.location.href = api('logout');
            }
        });
    });

    module.factory("AuthService", function($location, $q) {
        return AuthService;
    });

    module.factory("AuthRequireResolver", function($location, $q, AuthService) {
        return $q(function(resolve, reject) {
            AuthService.isLoggedIn().then(isLoggedIn => {
                if (isLoggedIn) {
                    AuthService.hasRole('billett.admin').then(hasRole => {
                        if (hasRole) {
                            resolve();
                        } else {
                            $location.path('/');
                            reject();
                        }
                    }, reject);
                } else {
                    window.location.href = 'login?url='+encodeURIComponent($location.path());
                }
            }, reject);
        });
    });
})();
<commit_msg>Redirect to admin page after login request<commit_after>import {api} from '../api';
import AuthService from './AuthService';
const angular = require('angular');

module.exports = 'billett.auth';

(function() {
    'use strict';

    var module = angular.module('billett.auth', [
        'ui.router'
    ]);

    module.config(function($stateProvider) {
        $stateProvider.state('login', {
            url: '/login',
            template: 'Går til logg inn side',
            controller: function($location) {
                window.location.href = api('login?url=a');
            }
        }).
        state('logout', {
            url: '/logout',
            template: 'Logger ut',
            controller: function() {
                window.location.href = api('logout');
            }
        });
    });

    module.factory("AuthService", function($location, $q) {
        return AuthService;
    });

    module.factory("AuthRequireResolver", function($location, $q, AuthService) {
        return $q(function(resolve, reject) {
            AuthService.isLoggedIn().then(isLoggedIn => {
                if (isLoggedIn) {
                    AuthService.hasRole('billett.admin').then(hasRole => {
                        if (hasRole) {
                            resolve();
                        } else {
                            $location.path('/');
                            reject();
                        }
                    }, reject);
                } else {
                    window.location.href = 'login?url='+encodeURIComponent($location.path());
                }
            }, reject);
        });
    });
})();
<|endoftext|>


<commit_before>/*
 Copyright (c) 2013, Yahoo! Inc.  All rights reserved.
 Copyrights licensed under the New BSD License. See the accompanying LICENSE file for terms.
 */
var path = require('path'),
    fs = require('fs'),
    core = require('./core'),
    istanbul = require('istanbul'),
    bodyParser = require('body-parser'),
    ASSETS_DIR = istanbul.assetsDir,
    existsSync = fs.existsSync || path.existsSync,
    url = require('url'),
    zs = require('archiver'),
    ZipWriter = require('./zip-writer'),
    express = require('express'),
    Report = istanbul.Report,
    Collector = istanbul.Collector,
    utils = istanbul.utils,
    JS_RE = /\.js$/;

function createHandler(opts) {
    /*jslint nomen: true */
    opts = opts || {};

    var app = express();
    app.use(bodyParser.urlencoded({ extended: true }));
    app.use(bodyParser.json());

    //show main page for coverage report for /
    app.get('/', function (req, res) {
        var origUrl = url.parse(req.originalUrl).pathname,
            origLength = origUrl.length;
        if (origUrl.charAt(origLength - 1) !== '/') {
            origUrl += '/';
        }
        core.render(null, res, origUrl);
    });

    //show page for specific file/ dir for /show?file=/path/to/file
    app.get('/show', function (req, res) {
        var origUrl = url.parse(req.originalUrl).pathname,
            u = url.parse(req.url).pathname,
            pos = origUrl.indexOf(u),
            file = req.query.p;
        if (pos >= 0) {
            origUrl = origUrl.substring(0, pos);
        }
        if (!file) {
            res.setHeader('Content-type', 'text/plain');
            return res.end('[p] parameter must be specified');
        }
        core.render(file, res, origUrl);
    });

    //send static file for /asset/asset-name
    app.get('/asset/:name', function (req, res) {
        res.sendfile(path.resolve(ASSETS_DIR, req.params.name));
    });

    //reset coverage to baseline on POST /reset
    app.post('/reset', function (req, res) {
        core.restoreBaseline();
        res.json({ ok: true });
    });

    //opt-in to allow resets on GET as well (useful for easy browser-based demos :)
    if (opts.resetOnGet) {
        app.get('/reset', function (req, res) {
            core.restoreBaseline();
            res.json({ ok: true });
        });
    }

    //return global coverage object on /object as JSON
    app.get('/object', function (req, res) {
        res.json(core.getCoverageObject() || {});
    });

    //send self-contained download package with coverage and reports on /download
    app.get('/download', function (req, res) {
        var stream = zs.createZip(),
            writer = new ZipWriter(stream, process.cwd()),
            coverageObject = core.getCoverageObject() || {},
            collector = new Collector(),
            baseDir = process.cwd(),
            reports = [
                Report.create('html', { writer: writer, dir: path.join(baseDir, 'lcov-report') }),
                Report.create('lcovonly', { writer: writer, dir: baseDir })
            ];

        utils.removeDerivedInfo(coverageObject);
        collector.add(coverageObject);

        res.statusCode = 200;
        res.setHeader('Content-type', 'application/zip');
        res.setHeader('Content-Disposition', 'attachment; filename=coverage.zip');
        stream.pipe(res);
        writer.writeFile('coverage.json', function (w) {
            w.write(JSON.stringify(coverageObject, undefined, 4));
        });
        reports.forEach(function (report) {
            report.writeReport(collector);
        });
        writer.done();
    });

    //merge client coverage posted from browser
    app.post('/client', function (req, res) {
        var body = req.body;
        if (!(body && typeof body === 'object')) { //probably needs to be more robust
            return res.send(400, 'Please post an object with content-type: application/json');
        }
        core.mergeClientCoverage(body);
        res.json({ok: true});
    });

    return app;
}

function defaultClientMatcher(req) {
    var parsed = url.parse(req.url);
    return parsed.pathname && parsed.pathname.match(JS_RE);
}

function defaultPathTransformer(root) {
    return function (req) {
        var parsed = url.parse(req.url),
            pathName = parsed.pathname;
        if (pathName && pathName.charAt(0) === '/') {
            pathName = pathName.substring(1);
        }
        return path.resolve(root, pathName);
    };
}

function clientHandler(matcher, pathTransformer, opts) {
    var verbose = opts.verbose;

    return function (req, res, next) {

        if (!matcher(req)) { return next(); }
        var fullPath = pathTransformer(req);
        if (!fullPath) { return next(); }

        if (!core.getInstrumenter()) {
            console.error('No instrumenter set up, please call createHandler() before you use the client middleware');
            return next();
        }
        if (!existsSync(fullPath)) {
            console.warn('Could not find file [' + fullPath + '], ignoring');
            return next();
        }
        fs.readFile(fullPath, 'utf8', function (err, contents) {
            var instrumented;
            if (err) {
                console.warn('Error reading file: ' + fullPath);
                return next();
            }
            try {
                instrumented = core.getInstrumenter().instrumentSync(contents, fullPath);
                if (verbose) { console.log('Sending instrumented code for: ' + fullPath + ', url:' + req.url); }
                res.setHeader('Content-type', 'application/javascript');
                return res.send(instrumented);
            } catch (ex) {
                console.warn('Error instrumenting file:' + fullPath);
                return next();
            }
        });
    };
}

function createClientHandler(root, opts) {
    opts = opts || {};

    var app = express(),
        matcher = opts.matcher || defaultClientMatcher,
        pathTransformer = opts.pathTransformer || defaultPathTransformer(root);
    app.get('*', clientHandler(matcher, pathTransformer, opts));
    return app;
}

module.exports = {
    createClientHandler: createClientHandler,
    createHandler: createHandler,
    hookLoader: core.hookLoader
};

<commit_msg>Set the default max file size limit to 100mb for express middlewares: json and urlencode<commit_after>/*
 Copyright (c) 2013, Yahoo! Inc.  All rights reserved.
 Copyrights licensed under the New BSD License. See the accompanying LICENSE file for terms.
 */
var path = require('path'),
    fs = require('fs'),
    core = require('./core'),
    istanbul = require('istanbul'),
    bodyParser = require('body-parser'),
    ASSETS_DIR = istanbul.assetsDir,
    existsSync = fs.existsSync || path.existsSync,
    url = require('url'),
    zs = require('archiver'),
    ZipWriter = require('./zip-writer'),
    express = require('express'),
    Report = istanbul.Report,
    Collector = istanbul.Collector,
    utils = istanbul.utils,
    JS_RE = /\.js$/;

/**
 * Set default max limit to 100mb for incoming JSON and urlencoded
 * @type {String}
 */
var fileSizeMaximum = '100mb';
var isForceExtended = true;

function createHandler(opts) {
    /*jslint nomen: true */
    opts = opts || {};

    var app = express();
    // using separete options objects to maintain readability as the objects are getting more complex
    var urlOptions = { extended: isForceExtended, limit: fileSizeMaximum };
    var jsonOptions = { limit: fileSizeMaximum };

    app.use(bodyParser.urlencoded(urlOptions));
    app.use(bodyParser.json(jsonOptions));

    //show main page for coverage report for /
    app.get('/', function (req, res) {
        var origUrl = url.parse(req.originalUrl).pathname,
            origLength = origUrl.length;
        if (origUrl.charAt(origLength - 1) !== '/') {
            origUrl += '/';
        }
        core.render(null, res, origUrl);
    });

    //show page for specific file/ dir for /show?file=/path/to/file
    app.get('/show', function (req, res) {
        var origUrl = url.parse(req.originalUrl).pathname,
            u = url.parse(req.url).pathname,
            pos = origUrl.indexOf(u),
            file = req.query.p;
        if (pos >= 0) {
            origUrl = origUrl.substring(0, pos);
        }
        if (!file) {
            res.setHeader('Content-type', 'text/plain');
            return res.end('[p] parameter must be specified');
        }
        core.render(file, res, origUrl);
    });

    //send static file for /asset/asset-name
    app.get('/asset/:name', function (req, res) {
        res.sendfile(path.resolve(ASSETS_DIR, req.params.name));
    });

    //reset coverage to baseline on POST /reset
    app.post('/reset', function (req, res) {
        core.restoreBaseline();
        res.json({ ok: true });
    });

    //opt-in to allow resets on GET as well (useful for easy browser-based demos :)
    if (opts.resetOnGet) {
        app.get('/reset', function (req, res) {
            core.restoreBaseline();
            res.json({ ok: true });
        });
    }

    //return global coverage object on /object as JSON
    app.get('/object', function (req, res) {
        res.json(core.getCoverageObject() || {});
    });

    //send self-contained download package with coverage and reports on /download
    app.get('/download', function (req, res) {
        var stream = zs.createZip(),
            writer = new ZipWriter(stream, process.cwd()),
            coverageObject = core.getCoverageObject() || {},
            collector = new Collector(),
            baseDir = process.cwd(),
            reports = [
                Report.create('html', { writer: writer, dir: path.join(baseDir, 'lcov-report') }),
                Report.create('lcovonly', { writer: writer, dir: baseDir })
            ];

        utils.removeDerivedInfo(coverageObject);
        collector.add(coverageObject);

        res.statusCode = 200;
        res.setHeader('Content-type', 'application/zip');
        res.setHeader('Content-Disposition', 'attachment; filename=coverage.zip');
        stream.pipe(res);
        writer.writeFile('coverage.json', function (w) {
            w.write(JSON.stringify(coverageObject, undefined, 4));
        });
        reports.forEach(function (report) {
            report.writeReport(collector);
        });
        writer.done();
    });

    //merge client coverage posted from browser
    app.post('/client', function (req, res) {
        var body = req.body;
        if (!(body && typeof body === 'object')) { //probably needs to be more robust
            return res.send(400, 'Please post an object with content-type: application/json');
        }
        core.mergeClientCoverage(body);
        res.json({ok: true});
    });

    return app;
}

function defaultClientMatcher(req) {
    var parsed = url.parse(req.url);
    return parsed.pathname && parsed.pathname.match(JS_RE);
}

function defaultPathTransformer(root) {
    return function (req) {
        var parsed = url.parse(req.url),
            pathName = parsed.pathname;
        if (pathName && pathName.charAt(0) === '/') {
            pathName = pathName.substring(1);
        }
        return path.resolve(root, pathName);
    };
}

function clientHandler(matcher, pathTransformer, opts) {
    var verbose = opts.verbose;

    return function (req, res, next) {

        if (!matcher(req)) { return next(); }
        var fullPath = pathTransformer(req);
        if (!fullPath) { return next(); }

        if (!core.getInstrumenter()) {
            console.error('No instrumenter set up, please call createHandler() before you use the client middleware');
            return next();
        }
        if (!existsSync(fullPath)) {
            console.warn('Could not find file [' + fullPath + '], ignoring');
            return next();
        }
        fs.readFile(fullPath, 'utf8', function (err, contents) {
            var instrumented;
            if (err) {
                console.warn('Error reading file: ' + fullPath);
                return next();
            }
            try {
                instrumented = core.getInstrumenter().instrumentSync(contents, fullPath);
                if (verbose) { console.log('Sending instrumented code for: ' + fullPath + ', url:' + req.url); }
                res.setHeader('Content-type', 'application/javascript');
                return res.send(instrumented);
            } catch (ex) {
                console.warn('Error instrumenting file:' + fullPath);
                return next();
            }
        });
    };
}

function createClientHandler(root, opts) {
    opts = opts || {};

    var app = express(),
        matcher = opts.matcher || defaultClientMatcher,
        pathTransformer = opts.pathTransformer || defaultPathTransformer(root);
    app.get('*', clientHandler(matcher, pathTransformer, opts));
    return app;
}

module.exports = {
    createClientHandler: createClientHandler,
    createHandler: createHandler,
    hookLoader: core.hookLoader
};

<|endoftext|>