convert to yii2

master
cornernote 2015-08-08 04:01:35 +09:30
parent 926ec2ba12
commit 4b3022f503
29 changed files with 1341 additions and 350 deletions

3
.bowerrc Normal file
View File

@ -0,0 +1,3 @@
{
"directory" : "vendor/bower"
}

7
.gitignore vendored
View File

@ -1,3 +1,6 @@
.idea
/app/vendor/
app/data/bower.db.sqlite
.DS_Store
Thumbs.db
composer.phar
vendor/
_bak/

View File

@ -1 +1 @@
web: app/vendor/bin/heroku-php-apache2 public/
web: vendor/bin/heroku-php-apache2 web/

View File

@ -1,66 +0,0 @@
# Slim Bower Server
This is a PHP based implementation of a [bower-server](https://github.com/twitter/bower-server) used by the excellent package manager [Bower](https://github.com/twitter/bower).
It's built using:
- [Slim PHP Framework](https://github.com/codeguy/Slim)
- [PHPActiveRecord](https://github.com/kla/php-activerecord)
and currently configured OTB to use sqlite (Why? see below)
### Overview
The original aim of this project was to get a server up running as fast as possible to evaluate the usage of Bower where I currently work for managing code dependencies between projects.
Since we already had an existing development PHP server available it made sense to use this rather than setting up a new VM with node.js, DB etc. If you've worked in corporate environments before you'll understand why.
It currently uses an sqlite database, but due to **PHPActiveRecord** being used it's very easy to switch to another database (see app/config.php).
### Installation
Installation will vary depending upon your server configuration, but the basics are detailed below.
#### Checkout
```
> git clone https://github.com/indieisaconcept/slim-bower-server.git myproject
> cd myproject
> rm -rf .git (should you wish to add to your own version control)
```
#### Dependencies
Dependencies are managed using Composer.
```
> curl -s https://getcomposer.org/installer | php
> php composer.phar install
```
### Usage
Ensure you update your .bowerrc either at a global or project level to use your custom server endpoint.
```
{
...
"endpoint": 'http://some.host.com.au'
}
```
#### Create package
curl http://some.host.com.au/packages -v -F 'name=jquery' -F 'url=git://github.com/jquery/jquery.git'
#### Find package
curl http://some.host.com.au/packages/jquery
{"name":"jquery","url":"git://github.com/jquery/jquery.git"}
#### Search package
curl http://some.host.com.au/packages/search/jquery
[{"name":"jquery","url":"git://github.com/jquery/jquery.git"}, {"name":"jquery-ui","url":"git://github.com/jquery/jquery-ui.git"}]

View File

@ -1,13 +0,0 @@
<?php
// CONFIG
$url = parse_url(getenv('DATABASE_URL'));
$config = array(
'database' => array(
'models' => '../app/models',
'connection' => array(
'production' => 'pgsql://' . $url['user'] . ':' . $url['pass'] . '@' . $url['host'] . '/' . substr($url['path'], 1),
'development' => 'sqlite://../app/data/bower.db.sqlite',
),
),
);

View File

@ -1,8 +0,0 @@
<?php
ActiveRecord\Config::initialize(function($cfg) use ($config) {
$database = $config['database'];
$cfg->set_model_directory($database['models']);
$cfg->set_connections($database['connection']);
$cfg->set_default_connection(getenv('APP_ENV') ? getenv('APP_ENV') : 'development');
});

View File

@ -1,8 +0,0 @@
CREATE TABLE packages (
id SERIAL,
name varchar(255) NOT NULL UNIQUE ,
url varchar(512) NOT NULL UNIQUE ,
hits integer NOT NULL DEFAULT 0,
created_at timestamp NOT NULL,
updated_at timestamp NOT NULL
);

View File

@ -1,12 +0,0 @@
CREATE TABLE "packages" (
"id" INTEGER PRIMARY KEY NOT NULL check(typeof("id") = 'integer'),
"name" VARCHAR NOT NULL UNIQUE ,
"url" VARCHAR NOT NULL UNIQUE ,
"hits" INTEGER NOT NULL DEFAULT 0,
"created_at" DATETIME NOT NULL,
"updated_at" DATETIME NOT NULL
);
CREATE INDEX "packages_name" ON "packages" ("name");

View File

@ -1,23 +0,0 @@
<?php
class Package extends ActiveRecord\Model {
static $validates_uniqueness_of = array(
array(
array('name', 'url'),
'message' => 'must be unique'
)
);
static $validates_presence_of = array(
array('name', 'allow_null' => FALSE, 'allow_blank' => FALSE, 'message' => 'is required', 'on' => 'create'),
array('url', 'allow_null' => FALSE, 'allow_blank' => FALSE, 'message' => 'is required', 'on' => 'create')
);
static $validates_format_of = array(
array('url', 'with' => '/^git\:\/\//', 'message' => 'must be a valid git:// url' , 'on' => 'create')
);
}
?>

View File

@ -1,7 +0,0 @@
<?php
$app->get('/', function () {
echo "<h1>Not Found</h1>";
});
?>

View File

@ -1,134 +0,0 @@
<?php
// process
// Porcess a phpactiverecord recordset
$process = function ($packages) {
// attributes
// Return require attributes from record
function attributes ($pkg) {
return array(
'name' => $pkg->name,
'url' => $pkg->url
);
};
$results = null;
if (isset($packages)) {
$results = array();
if (is_array($packages)) {
foreach ($packages as $package) {
array_push($results, attributes($package));
}
} else {
$results = attributes($packages);
}
$results = json_encode($results);
}
return $results;
};
// POST /packages
// > Accept: application/json
//
// {
// name: 'package-name',
// url: 'git-url'
// }
//
// < 200
$app->post('/packages', function () use ($app) {
$attributes = $app->request()->post();
$package = new Package(array(
'name' => $attributes['name'],
'url' => $attributes['url']
));
if ($package->is_valid()) {
$package->save();
$app->response()->status(201);
} else {
$app->response()->status(400);
}
});
// GET /packages
// < 200
// < Content-Type: application/json
//
// [{
// name: 'package-name',
// url: 'git-url'
// }]
$app->get('/packages', function () use ($app, $process) {
$result = $process(Package::find('all', array('order' => 'name DESC')));
if (isset($result)) {
$app->response()->header('Content-Type', 'application/json');
echo $result;
}
});
// GET /packages/{parameters}
// < 200
// < Content-Type: application/json
//
// {
// name: 'package-name',
// url: 'git-url'
// }
$app->get('/packages/:name', function ($name) use ($app, $process) {
$package = Package::find(array('conditions' => array('name = ?', $name)));
$result = $process($package);
if (isset($result)) {
$package->update_attributes(array('hits' => $package->hits + 1));
$app->response()->header('Content-Type', 'application/json');
echo $result;
} else {
$app->response()->status(404);
}
});
// GET /packages/search/{parameters}
// < 200
//
// [{
// name: 'package-name',
// url: 'git-url'
// }]
$app->get('/packages/search/:name', function ($name) use ($app, $process) {
$packages = Package::find('all', array('conditions' => array('name LIKE "%' . $name . '%"'), 'order' => 'name DESC'));
$result = $process($packages);
if (isset($result)) {
$app->response()->header('Content-Type', 'application/json');
echo $result;
}
});
?>

17
assets/AppAsset.php Normal file
View File

@ -0,0 +1,17 @@
<?php
namespace app\assets;
use yii\web\AssetBundle;
class AppAsset extends AssetBundle
{
public $sourcePath = '@app/assets/web';
public $css = [
'css/site.css',
];
public $depends = [
'yii\web\YiiAsset',
'yii\bootstrap\BootstrapAsset',
];
}

91
assets/web/css/site.css Normal file
View File

@ -0,0 +1,91 @@
html,
body {
height: 100%;
}
.wrap {
min-height: 100%;
height: auto;
margin: 0 auto -60px;
padding: 0 0 60px;
}
.wrap > .container {
padding: 70px 15px 20px;
}
.footer {
height: 60px;
background-color: #f5f5f5;
border-top: 1px solid #ddd;
padding-top: 20px;
}
.jumbotron {
text-align: center;
background-color: transparent;
}
.jumbotron .btn {
font-size: 21px;
padding: 14px 24px;
}
.not-set {
color: #c55;
font-style: italic;
}
/* add sorting icons to gridview sort links */
a.asc:after, a.desc:after {
position: relative;
top: 1px;
display: inline-block;
font-family: 'Glyphicons Halflings';
font-style: normal;
font-weight: normal;
line-height: 1;
padding-left: 5px;
}
a.asc:after {
content: /*"\e113"*/ "\e151";
}
a.desc:after {
content: /*"\e114"*/ "\e152";
}
.sort-numerical a.asc:after {
content: "\e153";
}
.sort-numerical a.desc:after {
content: "\e154";
}
.sort-ordinal a.asc:after {
content: "\e155";
}
.sort-ordinal a.desc:after {
content: "\e156";
}
.grid-view th {
white-space: nowrap;
}
.hint-block {
display: block;
margin-top: 5px;
color: #999;
}
.error-summary {
color: #a94442;
background: #fdf7f7;
border-left: 3px solid #eed3d7;
padding: 10px 20px;
margin: 0 0 15px 0;
}

View File

@ -1,12 +1,27 @@
{
"config": {
"vendor-dir": "app/vendor"
},
"name": "cornernote/minetest-bower",
"description": "Minetest Bower",
"homepage": "http://minetest-bower.herokuapp.com/",
"type": "project",
"license": "BSD-3-Clause",
"minimum-stability": "stable",
"require": {
"slim/slim": "2.*",
"php-activerecord/php-activerecord": "dev-master"
"php": ">=5.4.0",
"yiisoft/yii2": ">=2.0.5",
"yiisoft/yii2-bootstrap": "*"
},
"config": {
"process-timeout": 1800
},
"scripts": {
"post-create-project-cmd": [
"yii\\composer\\Installer::postCreateProject"
]
},
"extra": {
"asset-installer-paths": {
"npm-asset-library": "vendor/npm",
"bower-asset-library": "vendor/bower"
}
}
}
}

919
composer.lock generated
View File

@ -1,62 +1,252 @@
{
"hash": "c4d7a0adea03e9daab617a5e5b20ee66",
"_readme": [
"This file locks the dependencies of your project to a known state",
"Read more about it at https://getcomposer.org/doc/01-basic-usage.md#composer-lock-the-lock-file",
"This file is @generated automatically"
],
"hash": "479407875c975e7dbee0aefcb85e62d5",
"packages": [
{
"name": "php-activerecord/php-activerecord",
"version": "dev-master",
"name": "bower-asset/bootstrap",
"version": "v3.3.5",
"source": {
"type": "git",
"url": "https://github.com/kla/php-activerecord.git",
"reference": "e23921047955cfcf0c4e5abcce6d5d9b74092283"
"url": "https://github.com/twbs/bootstrap.git",
"reference": "16b48259a62f576e52c903c476bd42b90ab22482"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/kla/php-activerecord/zipball/e23921047955cfcf0c4e5abcce6d5d9b74092283",
"reference": "e23921047955cfcf0c4e5abcce6d5d9b74092283",
"url": "https://api.github.com/repos/twbs/bootstrap/zipball/16b48259a62f576e52c903c476bd42b90ab22482",
"reference": "16b48259a62f576e52c903c476bd42b90ab22482",
"shasum": ""
},
"require": {
"php": ">=5.3.0"
"bower-asset/jquery": ">=1.9.1"
},
"type": "library",
"autoload": {
"files": [
"ActiveRecord.php"
"type": "bower-asset-library",
"extra": {
"bower-asset-main": [
"less/bootstrap.less",
"dist/js/bootstrap.js"
],
"bower-asset-ignore": [
"/.*",
"_config.yml",
"CNAME",
"composer.json",
"CONTRIBUTING.md",
"docs",
"js/tests",
"test-infra"
]
},
"notification-url": "https://packagist.org/downloads/",
"license": [
"MIT"
],
"description": "php-activerecord is an open source ORM library based on the ActiveRecord pattern.",
"homepage": "http://www.phpactiverecord.org/",
"description": "The most popular front-end framework for developing responsive, mobile first projects on the web.",
"keywords": [
"activerecord",
"orm"
],
"time": "2013-02-20 04:42:10"
"css",
"framework",
"front-end",
"js",
"less",
"mobile-first",
"responsive",
"web"
]
},
{
"name": "slim/slim",
"version": "2.2.0",
"name": "bower-asset/jquery",
"version": "2.1.4",
"source": {
"type": "git",
"url": "https://github.com/codeguy/Slim",
"reference": "2.2.0"
"url": "https://github.com/jquery/jquery.git",
"reference": "7751e69b615c6eca6f783a81e292a55725af6b85"
},
"dist": {
"type": "zip",
"url": "https://github.com/codeguy/Slim/archive/2.2.0.zip",
"reference": "2.2.0",
"url": "https://api.github.com/repos/jquery/jquery/zipball/7751e69b615c6eca6f783a81e292a55725af6b85",
"reference": "7751e69b615c6eca6f783a81e292a55725af6b85",
"shasum": ""
},
"require-dev": {
"bower-asset/qunit": "1.14.0",
"bower-asset/requirejs": "2.1.10",
"bower-asset/sinon": "1.8.1",
"bower-asset/sizzle": "2.1.1-patch2"
},
"type": "bower-asset-library",
"extra": {
"bower-asset-main": "dist/jquery.js",
"bower-asset-ignore": [
"**/.*",
"build",
"dist/cdn",
"speed",
"test",
"*.md",
"AUTHORS.txt",
"Gruntfile.js",
"package.json"
]
},
"license": [
"MIT"
],
"keywords": [
"javascript",
"jquery",
"library"
]
},
{
"name": "bower-asset/jquery.inputmask",
"version": "3.1.63",
"source": {
"type": "git",
"url": "https://github.com/RobinHerbots/jquery.inputmask.git",
"reference": "c40c7287eadc31e341ebbf0c02352eb55b9cbc48"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/RobinHerbots/jquery.inputmask/zipball/c40c7287eadc31e341ebbf0c02352eb55b9cbc48",
"reference": "c40c7287eadc31e341ebbf0c02352eb55b9cbc48",
"shasum": ""
},
"require": {
"php": ">=5.3.0"
"bower-asset/jquery": ">=1.7"
},
"type": "bower-asset-library",
"extra": {
"bower-asset-main": [
"./dist/inputmask/jquery.inputmask.js",
"./dist/inputmask/jquery.inputmask.extensions.js",
"./dist/inputmask/jquery.inputmask.date.extensions.js",
"./dist/inputmask/jquery.inputmask.numeric.extensions.js",
"./dist/inputmask/jquery.inputmask.phone.extensions.js",
"./dist/inputmask/jquery.inputmask.regex.extensions.js"
],
"bower-asset-ignore": [
"**/.*",
"qunit/",
"nuget/",
"tools/",
"js/",
"*.md",
"build.properties",
"build.xml",
"jquery.inputmask.jquery.json"
]
},
"license": [
"http://opensource.org/licenses/mit-license.php"
],
"description": "jquery.inputmask is a jquery plugin which create an input mask.",
"keywords": [
"form",
"input",
"inputmask",
"jquery",
"mask",
"plugins"
]
},
{
"name": "bower-asset/punycode",
"version": "v1.3.2",
"source": {
"type": "git",
"url": "https://github.com/bestiejs/punycode.js.git",
"reference": "38c8d3131a82567bfef18da09f7f4db68c84f8a3"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/bestiejs/punycode.js/zipball/38c8d3131a82567bfef18da09f7f4db68c84f8a3",
"reference": "38c8d3131a82567bfef18da09f7f4db68c84f8a3",
"shasum": ""
},
"type": "bower-asset-library",
"extra": {
"bower-asset-main": "punycode.js",
"bower-asset-ignore": [
"coverage",
"tests",
".*",
"component.json",
"Gruntfile.js",
"node_modules",
"package.json"
]
}
},
{
"name": "bower-asset/yii2-pjax",
"version": "v2.0.4",
"source": {
"type": "git",
"url": "https://github.com/yiisoft/jquery-pjax.git",
"reference": "3f20897307cca046fca5323b318475ae9dac0ca0"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/yiisoft/jquery-pjax/zipball/3f20897307cca046fca5323b318475ae9dac0ca0",
"reference": "3f20897307cca046fca5323b318475ae9dac0ca0",
"shasum": ""
},
"require": {
"bower-asset/jquery": ">=1.8"
},
"type": "bower-asset-library",
"extra": {
"bower-asset-main": "./jquery.pjax.js",
"bower-asset-ignore": [
".travis.yml",
"Gemfile",
"Gemfile.lock",
"vendor/",
"script/",
"test/"
]
},
"license": [
"MIT"
]
},
{
"name": "cebe/markdown",
"version": "1.1.0",
"source": {
"type": "git",
"url": "https://github.com/cebe/markdown.git",
"reference": "54a2c49de31cc44e864ebf0500a35ef21d0010b2"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/cebe/markdown/zipball/54a2c49de31cc44e864ebf0500a35ef21d0010b2",
"reference": "54a2c49de31cc44e864ebf0500a35ef21d0010b2",
"shasum": ""
},
"require": {
"lib-pcre": "*",
"php": ">=5.4.0"
},
"require-dev": {
"cebe/indent": "*",
"facebook/xhprof": "*@dev",
"phpunit/phpunit": "4.1.*"
},
"bin": [
"bin/markdown"
],
"type": "library",
"extra": {
"branch-alias": {
"dev-master": "1.1.x-dev"
}
},
"autoload": {
"psr-0": {
"Slim": "."
"psr-4": {
"cebe\\markdown\\": ""
}
},
"notification-url": "https://packagist.org/downloads/",
@ -65,27 +255,670 @@
],
"authors": [
{
"name": "Josh Lockhart",
"email": "info@joshlockhart.com",
"homepage": "https://github.com/codeguy/"
"name": "Carsten Brandt",
"email": "mail@cebe.cc",
"homepage": "http://cebe.cc/",
"role": "Creator"
}
],
"description": "Slim Framework, a PHP micro framework",
"homepage": "http://github.com/codeguy/Slim",
"description": "A super fast, highly extensible markdown parser for PHP",
"homepage": "https://github.com/cebe/markdown#readme",
"keywords": [
"microframework",
"rest",
"router"
"extensible",
"fast",
"gfm",
"markdown",
"markdown-extra"
],
"time": "2012-12-13 02:15:50"
"time": "2015-03-06 05:28:07"
},
{
"name": "ezyang/htmlpurifier",
"version": "v4.6.0",
"source": {
"type": "git",
"url": "https://github.com/ezyang/htmlpurifier.git",
"reference": "6f389f0f25b90d0b495308efcfa073981177f0fd"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/ezyang/htmlpurifier/zipball/6f389f0f25b90d0b495308efcfa073981177f0fd",
"reference": "6f389f0f25b90d0b495308efcfa073981177f0fd",
"shasum": ""
},
"require": {
"php": ">=5.2"
},
"type": "library",
"autoload": {
"psr-0": {
"HTMLPurifier": "library/"
},
"files": [
"library/HTMLPurifier.composer.php"
]
},
"notification-url": "https://packagist.org/downloads/",
"license": [
"LGPL"
],
"authors": [
{
"name": "Edward Z. Yang",
"email": "admin@htmlpurifier.org",
"homepage": "http://ezyang.com"
}
],
"description": "Standards compliant HTML filter written in PHP",
"homepage": "http://htmlpurifier.org/",
"keywords": [
"html"
],
"time": "2013-11-30 08:25:19"
},
{
"name": "swiftmailer/swiftmailer",
"version": "v5.4.1",
"source": {
"type": "git",
"url": "https://github.com/swiftmailer/swiftmailer.git",
"reference": "0697e6aa65c83edf97bb0f23d8763f94e3f11421"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/swiftmailer/swiftmailer/zipball/0697e6aa65c83edf97bb0f23d8763f94e3f11421",
"reference": "0697e6aa65c83edf97bb0f23d8763f94e3f11421",
"shasum": ""
},
"require": {
"php": ">=5.3.3"
},
"require-dev": {
"mockery/mockery": "~0.9.1,<0.9.4"
},
"type": "library",
"extra": {
"branch-alias": {
"dev-master": "5.4-dev"
}
},
"autoload": {
"files": [
"lib/swift_required.php"
]
},
"notification-url": "https://packagist.org/downloads/",
"license": [
"MIT"
],
"authors": [
{
"name": "Chris Corbyn"
},
{
"name": "Fabien Potencier",
"email": "fabien@symfony.com"
}
],
"description": "Swiftmailer, free feature-rich PHP mailer",
"homepage": "http://swiftmailer.org",
"keywords": [
"email",
"mail",
"mailer"
],
"time": "2015-06-06 14:19:39"
},
{
"name": "yiisoft/yii2",
"version": "2.0.6",
"source": {
"type": "git",
"url": "https://github.com/yiisoft/yii2-framework.git",
"reference": "f42b2eb80f61992438661b01d0d74c6738e2ff38"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/yiisoft/yii2-framework/zipball/f42b2eb80f61992438661b01d0d74c6738e2ff38",
"reference": "f42b2eb80f61992438661b01d0d74c6738e2ff38",
"shasum": ""
},
"require": {
"bower-asset/jquery": "2.1.*@stable | 1.11.*@stable",
"bower-asset/jquery.inputmask": "3.1.*",
"bower-asset/punycode": "1.3.*",
"bower-asset/yii2-pjax": ">=2.0.1",
"cebe/markdown": "~1.0.0 | ~1.1.0",
"ext-mbstring": "*",
"ezyang/htmlpurifier": "4.6.*",
"lib-pcre": "*",
"php": ">=5.4.0",
"yiisoft/yii2-composer": "*"
},
"bin": [
"yii"
],
"type": "library",
"extra": {
"branch-alias": {
"dev-master": "2.0.x-dev"
}
},
"autoload": {
"psr-4": {
"yii\\": ""
}
},
"notification-url": "https://packagist.org/downloads/",
"license": [
"BSD-3-Clause"
],
"authors": [
{
"name": "Qiang Xue",
"email": "qiang.xue@gmail.com",
"homepage": "http://www.yiiframework.com/",
"role": "Founder and project lead"
},
{
"name": "Alexander Makarov",
"email": "sam@rmcreative.ru",
"homepage": "http://rmcreative.ru/",
"role": "Core framework development"
},
{
"name": "Maurizio Domba",
"homepage": "http://mdomba.info/",
"role": "Core framework development"
},
{
"name": "Carsten Brandt",
"email": "mail@cebe.cc",
"homepage": "http://cebe.cc/",
"role": "Core framework development"
},
{
"name": "Timur Ruziev",
"email": "resurtm@gmail.com",
"homepage": "http://resurtm.com/",
"role": "Core framework development"
},
{
"name": "Paul Klimov",
"email": "klimov.paul@gmail.com",
"role": "Core framework development"
}
],
"description": "Yii PHP Framework Version 2",
"homepage": "http://www.yiiframework.com/",
"keywords": [
"framework",
"yii2"
],
"time": "2015-08-05 22:00:30"
},
{
"name": "yiisoft/yii2-bootstrap",
"version": "2.0.4",
"source": {
"type": "git",
"url": "https://github.com/yiisoft/yii2-bootstrap.git",
"reference": "1b6b1e61cf91c3cdd517d6a7e71d30bb212e4af0"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/yiisoft/yii2-bootstrap/zipball/1b6b1e61cf91c3cdd517d6a7e71d30bb212e4af0",
"reference": "1b6b1e61cf91c3cdd517d6a7e71d30bb212e4af0",
"shasum": ""
},
"require": {
"bower-asset/bootstrap": "3.3.* | 3.2.* | 3.1.*",
"yiisoft/yii2": ">=2.0.4"
},
"type": "yii2-extension",
"extra": {
"branch-alias": {
"dev-master": "2.0.x-dev"
},
"asset-installer-paths": {
"npm-asset-library": "vendor/npm",
"bower-asset-library": "vendor/bower"
}
},
"autoload": {
"psr-4": {
"yii\\bootstrap\\": ""
}
},
"notification-url": "https://packagist.org/downloads/",
"license": [
"BSD-3-Clause"
],
"authors": [
{
"name": "Qiang Xue",
"email": "qiang.xue@gmail.com"
}
],
"description": "The Twitter Bootstrap extension for the Yii framework",
"keywords": [
"bootstrap",
"yii2"
],
"time": "2015-05-10 22:08:17"
},
{
"name": "yiisoft/yii2-composer",
"version": "2.0.3",
"source": {
"type": "git",
"url": "https://github.com/yiisoft/yii2-composer.git",
"reference": "ca8d23707ae47d20b0454e4b135c156f6da6d7be"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/yiisoft/yii2-composer/zipball/ca8d23707ae47d20b0454e4b135c156f6da6d7be",
"reference": "ca8d23707ae47d20b0454e4b135c156f6da6d7be",
"shasum": ""
},
"require": {
"composer-plugin-api": "1.0.0"
},
"type": "composer-plugin",
"extra": {
"class": "yii\\composer\\Plugin",
"branch-alias": {
"dev-master": "2.0.x-dev"
}
},
"autoload": {
"psr-4": {
"yii\\composer\\": ""
}
},
"notification-url": "https://packagist.org/downloads/",
"license": [
"BSD-3-Clause"
],
"authors": [
{
"name": "Qiang Xue",
"email": "qiang.xue@gmail.com"
}
],
"description": "The composer plugin for Yii extension installer",
"keywords": [
"composer",
"extension installer",
"yii2"
],
"time": "2015-03-01 06:22:44"
},
{
"name": "yiisoft/yii2-swiftmailer",
"version": "2.0.4",
"source": {
"type": "git",
"url": "https://github.com/yiisoft/yii2-swiftmailer.git",
"reference": "4ec435a89e30b203cea99770910fb5499cb3627a"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/yiisoft/yii2-swiftmailer/zipball/4ec435a89e30b203cea99770910fb5499cb3627a",
"reference": "4ec435a89e30b203cea99770910fb5499cb3627a",
"shasum": ""
},
"require": {
"swiftmailer/swiftmailer": "~5.0",
"yiisoft/yii2": ">=2.0.4"
},
"type": "yii2-extension",
"extra": {
"branch-alias": {
"dev-master": "2.0.x-dev"
}
},
"autoload": {
"psr-4": {
"yii\\swiftmailer\\": ""
}
},
"notification-url": "https://packagist.org/downloads/",
"license": [
"BSD-3-Clause"
],
"authors": [
{
"name": "Paul Klimov",
"email": "klimov.paul@gmail.com"
}
],
"description": "The SwiftMailer integration for the Yii framework",
"keywords": [
"email",
"mail",
"mailer",
"swift",
"swiftmailer",
"yii2"
],
"time": "2015-05-10 22:12:32"
}
],
"packages-dev": null,
"aliases": [
"packages-dev": [
{
"name": "bower-asset/typeahead.js",
"version": "v0.10.5",
"source": {
"type": "git",
"url": "https://github.com/twitter/typeahead.js.git",
"reference": "5f198b87d1af845da502ea9df93a5e84801ce742"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/twitter/typeahead.js/zipball/5f198b87d1af845da502ea9df93a5e84801ce742",
"reference": "5f198b87d1af845da502ea9df93a5e84801ce742",
"shasum": ""
},
"require": {
"bower-asset/jquery": ">=1.7"
},
"require-dev": {
"bower-asset/jasmine-ajax": "~1.3.1",
"bower-asset/jasmine-jquery": "~1.5.2",
"bower-asset/jquery": "~1.7"
},
"type": "bower-asset-library",
"extra": {
"bower-asset-main": "dist/typeahead.bundle.js"
}
},
{
"name": "fzaninotto/faker",
"version": "v1.5.0",
"source": {
"type": "git",
"url": "https://github.com/fzaninotto/Faker.git",
"reference": "d0190b156bcca848d401fb80f31f504f37141c8d"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/fzaninotto/Faker/zipball/d0190b156bcca848d401fb80f31f504f37141c8d",
"reference": "d0190b156bcca848d401fb80f31f504f37141c8d",
"shasum": ""
},
"require": {
"php": ">=5.3.3"
},
"require-dev": {
"phpunit/phpunit": "~4.0",
"squizlabs/php_codesniffer": "~1.5"
},
"suggest": {
"ext-intl": "*"
},
"type": "library",
"extra": {
"branch-alias": {
"dev-master": "1.5.x-dev"
}
},
"autoload": {
"psr-4": {
"Faker\\": "src/Faker/"
}
},
"notification-url": "https://packagist.org/downloads/",
"license": [
"MIT"
],
"authors": [
{
"name": "François Zaninotto"
}
],
"description": "Faker is a PHP library that generates fake data for you.",
"keywords": [
"data",
"faker",
"fixtures"
],
"time": "2015-05-29 06:29:14"
},
{
"name": "phpspec/php-diff",
"version": "v1.0.2",
"source": {
"type": "git",
"url": "https://github.com/phpspec/php-diff.git",
"reference": "30e103d19519fe678ae64a60d77884ef3d71b28a"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/phpspec/php-diff/zipball/30e103d19519fe678ae64a60d77884ef3d71b28a",
"reference": "30e103d19519fe678ae64a60d77884ef3d71b28a",
"shasum": ""
},
"type": "library",
"autoload": {
"psr-0": {
"Diff": "lib/"
}
},
"notification-url": "https://packagist.org/downloads/",
"license": [
"BSD-3-Clause"
],
"authors": [
{
"name": "Chris Boulton",
"homepage": "http://github.com/chrisboulton",
"role": "Original developer"
}
],
"description": "A comprehensive library for generating differences between two hashable objects (strings or arrays).",
"time": "2013-11-01 13:02:21"
},
{
"name": "yiisoft/yii2-codeception",
"version": "2.0.4",
"source": {
"type": "git",
"url": "https://github.com/yiisoft/yii2-codeception.git",
"reference": "de5007e7a99359597abbfe1c88dca3ce620061c5"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/yiisoft/yii2-codeception/zipball/de5007e7a99359597abbfe1c88dca3ce620061c5",
"reference": "de5007e7a99359597abbfe1c88dca3ce620061c5",
"shasum": ""
},
"require": {
"yiisoft/yii2": ">=2.0.4"
},
"type": "yii2-extension",
"extra": {
"branch-alias": {
"dev-master": "2.0.x-dev"
}
},
"autoload": {
"psr-4": {
"yii\\codeception\\": ""
}
},
"notification-url": "https://packagist.org/downloads/",
"license": [
"BSD-3-Clause"
],
"authors": [
{
"name": "Mark Jebri",
"email": "mark.github@yandex.ru"
}
],
"description": "The Codeception integration for the Yii framework",
"keywords": [
"codeception",
"yii2"
],
"time": "2015-05-10 22:08:30"
},
{
"name": "yiisoft/yii2-debug",
"version": "2.0.5",
"source": {
"type": "git",
"url": "https://github.com/yiisoft/yii2-debug.git",
"reference": "1b302e67521d46feb2413d9d96ca94ed82b39b0e"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/yiisoft/yii2-debug/zipball/1b302e67521d46feb2413d9d96ca94ed82b39b0e",
"reference": "1b302e67521d46feb2413d9d96ca94ed82b39b0e",
"shasum": ""
},
"require": {
"yiisoft/yii2": ">=2.0.4",
"yiisoft/yii2-bootstrap": "*"
},
"type": "yii2-extension",
"extra": {
"branch-alias": {
"dev-master": "2.0.x-dev"
}
},
"autoload": {
"psr-4": {
"yii\\debug\\": ""
}
},
"notification-url": "https://packagist.org/downloads/",
"license": [
"BSD-3-Clause"
],
"authors": [
{
"name": "Qiang Xue",
"email": "qiang.xue@gmail.com"
}
],
"description": "The debugger extension for the Yii framework",
"keywords": [
"debug",
"debugger",
"yii2"
],
"time": "2015-08-06 16:14:06"
},
{
"name": "yiisoft/yii2-faker",
"version": "2.0.3",
"source": {
"type": "git",
"url": "https://github.com/yiisoft/yii2-faker.git",
"reference": "b88ca69ee226a3610b2c26c026c3203d7ac50f6c"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/yiisoft/yii2-faker/zipball/b88ca69ee226a3610b2c26c026c3203d7ac50f6c",
"reference": "b88ca69ee226a3610b2c26c026c3203d7ac50f6c",
"shasum": ""
},
"require": {
"fzaninotto/faker": "*",
"yiisoft/yii2": "*"
},
"type": "yii2-extension",
"extra": {
"branch-alias": {
"dev-master": "2.0.x-dev"
}
},
"autoload": {
"psr-4": {
"yii\\faker\\": ""
}
},
"notification-url": "https://packagist.org/downloads/",
"license": [
"BSD-3-Clause"
],
"authors": [
{
"name": "Mark Jebri",
"email": "mark.github@yandex.ru"
}
],
"description": "Fixture generator. The Faker integration for the Yii framework.",
"keywords": [
"Fixture",
"faker",
"yii2"
],
"time": "2015-03-01 06:22:44"
},
{
"name": "yiisoft/yii2-gii",
"version": "2.0.4",
"source": {
"type": "git",
"url": "https://github.com/yiisoft/yii2-gii.git",
"reference": "e5a023e8779bd774194842ec1b8fb4917cf04007"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/yiisoft/yii2-gii/zipball/e5a023e8779bd774194842ec1b8fb4917cf04007",
"reference": "e5a023e8779bd774194842ec1b8fb4917cf04007",
"shasum": ""
},
"require": {
"bower-asset/typeahead.js": "0.10.*",
"phpspec/php-diff": ">=1.0.2",
"yiisoft/yii2": ">=2.0.4",
"yiisoft/yii2-bootstrap": "~2.0"
},
"type": "yii2-extension",
"extra": {
"branch-alias": {
"dev-master": "2.0.x-dev"
},
"asset-installer-paths": {
"npm-asset-library": "vendor/npm",
"bower-asset-library": "vendor/bower"
}
},
"autoload": {
"psr-4": {
"yii\\gii\\": ""
}
},
"notification-url": "https://packagist.org/downloads/",
"license": [
"BSD-3-Clause"
],
"authors": [
{
"name": "Qiang Xue",
"email": "qiang.xue@gmail.com"
}
],
"description": "The Gii extension for the Yii framework",
"keywords": [
"code generator",
"gii",
"yii2"
],
"time": "2015-05-10 22:09:31"
}
],
"aliases": [],
"minimum-stability": "stable",
"stability-flags": {
"php-activerecord/php-activerecord": 20
}
"stability-flags": [],
"prefer-stable": false,
"prefer-lowest": false,
"platform": {
"php": ">=5.4.0"
},
"platform-dev": []
}

19
config/db.php Normal file
View File

@ -0,0 +1,19 @@
<?php
if (YII_ENV == 'prod') {
$url = parse_url(getenv('DATABASE_URL'));
return [
'class' => 'yii\db\Connection',
'dsn' => 'pgsql:host=' . $url['host'] . ';dbname=' . substr($url['path'], 1),
'username' => $url['user'],
'password' => $url['pass'],
'charset' => 'utf8',
];
}
return [
'class' => 'yii\db\Connection',
'dsn' => 'mysql:host=localhost;dbname=minetest_bower',
'username' => 'root',
'password' => 'root',
'charset' => 'utf8',
];

29
config/web.php Normal file
View File

@ -0,0 +1,29 @@
<?php
defined('YII_ENV') or define('YII_ENV', 'dev');
$config = [
'id' => 'minetest-bower',
'basePath' => dirname(__DIR__),
'components' => [
'db' => require(__DIR__ . '/db.php'),
'errorHandler' => [
'errorAction' => 'site/error',
],
'request' => [
'cookieValidationKey' => getenv('APP_COOKIE_VALIDATION_KEY') or 'test',
],
'urlManager' => [
'enablePrettyUrl' => true,
'showScriptName' => false,
'rules' => [
'POST packages' => 'package/create',
'packages' => 'package/index',
'packages/search/<name:\w+>' => 'package/search',
'packages/<name:\w+>' => 'package/view',
],
],
],
];
return $config;

View File

@ -0,0 +1,66 @@
<?php
namespace app\controllers;
use app\models\Package;
use Yii;
use yii\filters\VerbFilter;
use yii\web\Controller;
use yii\web\HttpException;
use yii\web\Response;
class PackageController extends Controller
{
public $enableCsrfValidation = false;
public function behaviors()
{
return [
'verbs' => [
'class' => VerbFilter::className(),
'actions' => [
'create' => ['post'],
],
],
];
}
public function beforeAction($action)
{
Yii::$app->response->format = Response::FORMAT_JSON;
return parent::beforeAction($action);
}
public function actionCreate()
{
$package = new Package();
$package->setAttributes(Yii::$app->request->post());
if ($package->save()) {
Yii::$app->response->statusCode = 201;
return '';
}
throw new HttpException(400, json_encode($package->errors));
}
public function actionIndex()
{
return Package::find()->orderBy(['hits' => SORT_DESC])->all();
}
public function actionView($name = null)
{
$package = Package::find()->where(['name' => $name])->one();
if ($package) {
$package->hits++;
$package->save();
return $package;
}
throw new HttpException(404);
}
public function actionSearch($name)
{
return Package::find()->where(['name' => $name])->orderBy(['hits' => SORT_DESC])->all();
}
}

View File

@ -0,0 +1,29 @@
<?php
namespace app\controllers;
use Yii;
use yii\filters\AccessControl;
use yii\web\Controller;
use yii\filters\VerbFilter;
use app\models\LoginForm;
use app\models\ContactForm;
class SiteController extends Controller
{
public function actions()
{
return [
'error' => [
'class' => 'yii\web\ErrorAction',
],
];
}
public function actionIndex()
{
return $this->render('index');
}
}

71
models/Package.php Normal file
View File

@ -0,0 +1,71 @@
<?php
namespace app\models;
use Yii;
use yii\behaviors\TimestampBehavior;
/**
* This is the model class for table "{{%package}}".
*
* @property integer $id
* @property string $name
* @property string $url
* @property integer $hits
* @property string $created_at
* @property string $updated_at
*/
class Package extends \yii\db\ActiveRecord
{
/**
* @inheritdoc
*/
public static function tableName()
{
return '{{%package}}';
}
/**
* @inheritdoc
*/
public function rules()
{
return [
[['name', 'url'], 'required'],
[['name'], 'string', 'max' => 64],
[['url'], 'string', 'max' => 255],
[['name'], 'unique'],
[['url'], 'unique']
];
}
/**
* @inheritdoc
*/
public function attributeLabels()
{
return [
'id' => 'ID',
'name' => 'Name',
'url' => 'URL',
'hits' => 'Hits',
'created_at' => 'Created At',
'updated_at' => 'Updated At',
];
}
/**
* @inheritdoc
*/
public function behaviors()
{
return [
[
'class' => TimestampBehavior::className(),
'value' => function () {
return date('Y-m-d H:i:s');
},
],
];
}
}

View File

@ -1,10 +0,0 @@
RewriteEngine On
# Some hosts may require you to use the `RewriteBase` directive.
# If you need to use the `RewriteBase` directive, it should be the
# absolute physical path to the directory that contains this htaccess file.
#
# RewriteBase /
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^(.*)$ index.php [QSA,L]

View File

@ -1,14 +0,0 @@
<?php
require '../app/vendor/autoload.php';
$app = new \Slim\Slim();
require '../app/config.php';
require '../app/data/config.php';
require '../app/routes/default.php';
require '../app/routes/packages.php';
$app->run();
?>

2
runtime/.gitignore vendored Normal file
View File

@ -0,0 +1,2 @@
*
!.gitignore

56
views/layouts/main.php Normal file
View File

@ -0,0 +1,56 @@
<?php
/* @var $this \yii\web\View */
/* @var $content string */
use yii\helpers\Html;
use yii\bootstrap\Nav;
use yii\bootstrap\NavBar;
use yii\widgets\Breadcrumbs;
use app\assets\AppAsset;
AppAsset::register($this);
?>
<?php $this->beginPage() ?>
<!DOCTYPE html>
<html lang="<?= Yii::$app->language ?>">
<head>
<meta charset="<?= Yii::$app->charset ?>">
<meta name="viewport" content="width=device-width, initial-scale=1">
<?= Html::csrfMetaTags() ?>
<title><?= Html::encode($this->title) ?></title>
<?php $this->head() ?>
</head>
<body>
<?php $this->beginBody() ?>
<div class="wrap">
<?php
NavBar::begin([
'brandLabel' => 'Minetest Bower',
'brandUrl' => Yii::$app->homeUrl,
'options' => [
'class' => 'navbar-inverse navbar-fixed-top',
],
]);
echo Nav::widget([
'options' => ['class' => 'navbar-nav navbar-right'],
'items' => [
['label' => 'Home', 'url' => ['/site/index']],
],
]);
NavBar::end();
?>
<div class="container">
<?= Breadcrumbs::widget([
'links' => isset($this->params['breadcrumbs']) ? $this->params['breadcrumbs'] : [],
]) ?>
<?= $content ?>
</div>
</div>
<?php $this->endBody() ?>
</body>
</html>
<?php $this->endPage() ?>

27
views/site/error.php Normal file
View File

@ -0,0 +1,27 @@
<?php
/* @var $this yii\web\View */
/* @var $name string */
/* @var $message string */
/* @var $exception Exception */
use yii\helpers\Html;
$this->title = $name;
?>
<div class="site-error">
<h1><?= Html::encode($this->title) ?></h1>
<div class="alert alert-danger">
<?= nl2br(Html::encode($message)) ?>
</div>
<p>
The above error occurred while the Web server was processing your request.
</p>
<p>
Please contact us if you think this is a server error. Thank you.
</p>
</div>

9
views/site/index.php Normal file
View File

@ -0,0 +1,9 @@
<?php
/* @var $this yii\web\View */
$this->title = 'Minetest Bower';
?>
<div class="site-index">
</div>

2
web/assets/.gitignore vendored Normal file
View File

@ -0,0 +1,2 @@
*
!.gitignore

12
web/index.php Normal file
View File

@ -0,0 +1,12 @@
<?php
// comment out the following two lines when deployed to production
defined('YII_DEBUG') or define('YII_DEBUG', true);
defined('YII_ENV') or define('YII_ENV', 'dev');
require(__DIR__ . '/../vendor/autoload.php');
require(__DIR__ . '/../vendor/yiisoft/yii2/Yii.php');
$config = require(__DIR__ . '/../config/web.php');
(new yii\web\Application($config))->run();

2
web/robots.txt Normal file
View File

@ -0,0 +1,2 @@
User-agent: *
Disallow: