├── .bowerrc
├── .dockerignore
├── .editorconfig
├── .env-example
├── .gitignore
├── .travis.yml
├── CODE_OF_CONDUCT.md
├── CONTRIBUTING.md
├── LICENSE
├── README.md
├── app
├── .htaccess
├── AppCache.php
├── AppKernel.php
├── DoctrineMigrations
│ ├── Version20170701083607.php
│ ├── Version20170701083839.php
│ ├── Version20170907000538.php
│ ├── Version20170914142257.php
│ ├── Version20170915083636.php
│ ├── Version20170918155155.php
│ ├── Version20170930124648.php
│ ├── Version20170930171444.php
│ ├── Version20171003083933.php
│ └── Version20171004065248.php
├── Resources
│ ├── FOSUserBundle
│ │ └── views
│ │ │ ├── ChangePassword
│ │ │ ├── change_password.html.twig
│ │ │ └── change_password_content.html.twig
│ │ │ ├── Profile
│ │ │ ├── edit.html.twig
│ │ │ ├── edit_content.html.twig
│ │ │ ├── show.html.twig
│ │ │ └── show_content.html.twig
│ │ │ ├── Registration
│ │ │ ├── check_email.html.twig
│ │ │ ├── confirmed.html.twig
│ │ │ ├── email.txt.twig
│ │ │ ├── register.html.twig
│ │ │ └── register_content.html.twig
│ │ │ ├── Resetting
│ │ │ ├── check_email.html.twig
│ │ │ ├── email.txt.twig
│ │ │ ├── request.html.twig
│ │ │ ├── request_content.html.twig
│ │ │ ├── reset.html.twig
│ │ │ └── reset_content.html.twig
│ │ │ ├── Security
│ │ │ ├── login.html.twig
│ │ │ └── login_content.html.twig
│ │ │ └── layout.html.twig
│ ├── translations
│ │ └── dashboard.id.xlf
│ └── views
│ │ ├── area
│ │ ├── create.html.twig
│ │ ├── edit.html.twig
│ │ ├── index.html.twig
│ │ └── show.html.twig
│ │ ├── base.html.twig
│ │ ├── dashboard
│ │ └── index.html.twig
│ │ ├── device
│ │ ├── areas.html.twig
│ │ ├── create.html.twig
│ │ ├── index.html.twig
│ │ ├── resources.html.twig
│ │ └── show.html.twig
│ │ ├── field
│ │ ├── add.html.twig
│ │ ├── index.html.twig
│ │ └── show.html.twig
│ │ ├── inventory
│ │ └── index.html.twig
│ │ ├── navbar.html.twig
│ │ ├── plant
│ │ ├── create.html.twig
│ │ ├── edit.html.twig
│ │ ├── harvest.html.twig
│ │ ├── index.html.twig
│ │ └── show.html.twig
│ │ ├── reservoir
│ │ ├── index.html.twig
│ │ └── show.html.twig
│ │ ├── right-sidebar.html.twig
│ │ ├── seed
│ │ ├── create.html.twig
│ │ └── edit.html.twig
│ │ ├── settings
│ │ └── index.html.twig
│ │ ├── sidebar.html.twig
│ │ └── task
│ │ ├── create.html.twig
│ │ ├── index.html.twig
│ │ └── show.html.twig
└── config
│ ├── config.yml
│ ├── config_dev.yml
│ ├── config_prod.yml
│ ├── config_test.yml
│ ├── repository.yml
│ ├── routing.yml
│ ├── routing_dev.yml
│ ├── security.yml
│ └── services.yml
├── bin
├── console
└── symfony_requirements
├── bower.json
├── composer.json
├── composer.lock
├── docker-compose.dev.yml
├── docker-compose.yml
├── docker
└── app
│ ├── Dockerfile
│ ├── nginx.conf
│ └── tania-entrypoint
├── phpunit.xml.dist
├── readme-assets
├── project-dashboard.jpg
└── project-logo.png
├── src
├── .htaccess
└── AppBundle
│ ├── AppBundle.php
│ ├── Controller
│ ├── AreaController.php
│ ├── DashboardController.php
│ ├── DeviceController.php
│ ├── FieldController.php
│ ├── InventoryController.php
│ ├── PlantController.php
│ ├── ProfileController.php
│ ├── RegistrationController.php
│ ├── ReservoirController.php
│ ├── SettingsController.php
│ └── TaskController.php
│ ├── Data
│ ├── CategoryMaster.php
│ └── CountryList.php
│ ├── DataFixtures
│ └── ORM
│ │ ├── LoadResourceData.php
│ │ ├── LoadSeedCategory.php
│ │ └── LoadUserData.php
│ ├── DoctrineExtensions
│ └── Utils
│ │ └── AnyValue.php
│ ├── Entity
│ ├── Area.php
│ ├── AreasDevices.php
│ ├── Device.php
│ ├── Field.php
│ ├── Plant.php
│ ├── Reservoir.php
│ ├── Resource.php
│ ├── ResourcesDevices.php
│ ├── Seed.php
│ ├── SeedCategory.php
│ ├── Setting.php
│ ├── Task.php
│ └── User.php
│ ├── Form
│ ├── AreaDeviceType.php
│ ├── AreaType.php
│ ├── DeviceType.php
│ ├── FieldType.php
│ ├── PlantHarvestType.php
│ ├── PlantType.php
│ ├── RegistrationFormType.php
│ ├── ReservoirType.php
│ ├── ResourceDeviceType.php
│ ├── SeedType.php
│ ├── SettingType.php
│ └── TaskType.php
│ └── Repository
│ ├── AbstractRepository.php
│ ├── PlantRepository.php
│ └── TaskRepository.php
├── tests
└── AppBundle
│ └── Controller
│ ├── AreaControllerTest.php
│ ├── DashboardControllerTest.php
│ ├── DeviceControllerTest.php
│ ├── FieldControllerTest.php
│ ├── InventoryControllerTest.php
│ ├── PlantControllerTest.php
│ ├── ReservoirControllerTest.php
│ └── TaskControllerTest.php
├── var
├── SymfonyRequirements.php
├── cache
│ └── .gitkeep
├── logs
│ └── .gitkeep
└── sessions
│ └── .gitkeep
├── web.config
└── web
├── .htaccess
├── app.php
├── apple-touch-icon.png
├── assets
├── css
│ ├── .DS_Store
│ ├── bootstrap-theme.css
│ ├── bootstrap-theme.min.css
│ ├── bootstrap.css
│ ├── bootstrap.min.css
│ ├── material-design-icons
│ │ ├── css
│ │ │ ├── material-design-iconic-font.css
│ │ │ └── material-design-iconic-font.min.css
│ │ ├── fonts
│ │ │ ├── Material-Design-Iconic-Font.eot
│ │ │ ├── Material-Design-Iconic-Font.svg
│ │ │ ├── Material-Design-Iconic-Font.ttf
│ │ │ ├── Material-Design-Iconic-Font.woff
│ │ │ └── Material-Design-Iconic-Font.woff2
│ │ └── less
│ │ │ ├── aliases.less
│ │ │ ├── border.less
│ │ │ ├── core.less
│ │ │ ├── fixed-width.less
│ │ │ ├── icons.less
│ │ │ ├── list.less
│ │ │ ├── material-design-iconic-font.less
│ │ │ ├── path.less
│ │ │ ├── pulled.less
│ │ │ ├── rotated.less
│ │ │ ├── sizes.less
│ │ │ ├── spinned.less
│ │ │ ├── stacked.less
│ │ │ └── variables.less
│ ├── non-responsive.css
│ ├── select2.min.css
│ ├── style.css
│ ├── style.min.css
│ └── tania.css
├── fonts
│ ├── glyphicons-halflings-regular.eot
│ ├── glyphicons-halflings-regular.svg
│ ├── glyphicons-halflings-regular.ttf
│ ├── glyphicons-halflings-regular.woff
│ └── glyphicons-halflings-regular.woff2
├── img
│ ├── favicon.png
│ ├── logo.png
│ ├── plant-basil.jpg
│ └── tania.png
├── js
│ ├── area.js
│ ├── bootstrap.js
│ ├── bootstrap.min.js
│ ├── dashboard.js
│ ├── field-map-show.js
│ ├── field-map.js
│ ├── jquery-ui
│ │ └── jquery-ui.min.js
│ ├── jquery.min.js
│ ├── js-cookie.js
│ ├── main.js
│ ├── npm.js
│ ├── paho-mqtt.js
│ ├── perfect-scrollbar
│ │ ├── perfect-scrollbar.jquery.js
│ │ ├── perfect-scrollbar.jquery.min.js
│ │ ├── perfect-scrollbar.js
│ │ └── perfect-scrollbar.min.js
│ ├── plant.js
│ └── task.js
└── lib
│ ├── .DS_Store
│ └── roboto
│ ├── Roboto-Black.eot
│ ├── Roboto-Black.svg
│ ├── Roboto-Black.ttf
│ ├── Roboto-Black.woff
│ ├── Roboto-Black.woff2
│ ├── Roboto-BlackItalic.eot
│ ├── Roboto-BlackItalic.svg
│ ├── Roboto-BlackItalic.ttf
│ ├── Roboto-BlackItalic.woff
│ ├── Roboto-BlackItalic.woff2
│ ├── Roboto-Bold.eot
│ ├── Roboto-Bold.svg
│ ├── Roboto-Bold.ttf
│ ├── Roboto-Bold.woff
│ ├── Roboto-Bold.woff2
│ ├── Roboto-BoldItalic.eot
│ ├── Roboto-BoldItalic.svg
│ ├── Roboto-BoldItalic.ttf
│ ├── Roboto-BoldItalic.woff
│ ├── Roboto-BoldItalic.woff2
│ ├── Roboto-Light.eot
│ ├── Roboto-Light.svg
│ ├── Roboto-Light.ttf
│ ├── Roboto-Light.woff
│ ├── Roboto-Light.woff2
│ ├── Roboto-LightItalic.eot
│ ├── Roboto-LightItalic.svg
│ ├── Roboto-LightItalic.ttf
│ ├── Roboto-LightItalic.woff
│ ├── Roboto-LightItalic.woff2
│ ├── Roboto-Medium.eot
│ ├── Roboto-Medium.svg
│ ├── Roboto-Medium.ttf
│ ├── Roboto-Medium.woff
│ ├── Roboto-Medium.woff2
│ ├── Roboto-MediumItalic.eot
│ ├── Roboto-MediumItalic.svg
│ ├── Roboto-MediumItalic.ttf
│ ├── Roboto-MediumItalic.woff
│ ├── Roboto-MediumItalic.woff2
│ ├── Roboto-Regular.eot
│ ├── Roboto-Regular.svg
│ ├── Roboto-Regular.ttf
│ ├── Roboto-Regular.woff
│ ├── Roboto-Regular.woff2
│ ├── Roboto-RegularItalic.eot
│ ├── Roboto-RegularItalic.svg
│ ├── Roboto-RegularItalic.ttf
│ ├── Roboto-RegularItalic.woff
│ ├── Roboto-RegularItalic.woff2
│ ├── Roboto-Thin.eot
│ ├── Roboto-Thin.svg
│ ├── Roboto-Thin.ttf
│ ├── Roboto-Thin.woff
│ ├── Roboto-Thin.woff2
│ ├── Roboto-ThinItalic.eot
│ ├── Roboto-ThinItalic.svg
│ ├── Roboto-ThinItalic.ttf
│ ├── Roboto-ThinItalic.woff
│ └── Roboto-ThinItalic.woff2
├── config.php
├── debug.html
├── favicon.ico
├── robots.txt
└── uploads
├── areas
└── index.html
├── fields
└── index.html
└── seeds
└── index.html
/.bowerrc:
--------------------------------------------------------------------------------
1 | {
2 | "directory": "web/vendor"
3 | }
4 |
--------------------------------------------------------------------------------
/.dockerignore:
--------------------------------------------------------------------------------
1 | /.web-server-pid
2 | /app/config/parameters.yml
3 | /build/
4 | /phpunit.xml
5 | /var/*
6 | !/var/cache
7 | /var/cache/*
8 | !var/cache/.gitkeep
9 | !/var/logs
10 | /var/logs/*
11 | !var/logs/.gitkeep
12 | !/var/sessions
13 | /var/sessions/*
14 | !var/sessions/.gitkeep
15 | !var/SymfonyRequirements.php
16 | /vendor/
17 | /web/bundles/
18 | /web/uploads/areas/*.png
19 | /web/uploads/areas/*.jpg
20 | /web/uploads/areas/*.gif
21 | /web/uploads/fields/*.png
22 | /web/uploads/fields/*.jpg
23 | /web/uploads/fields/*.gif
24 | /web/uploads/seeds/*.png
25 | /web/uploads/seeds/*.jpg
26 | /web/uploads/seeds/*.gif
27 | /web/uploads/areas/*.PNG
28 | /web/uploads/areas/*.JPG
29 | /web/uploads/areas/*.GIF
30 | /web/uploads/fields/*.PNG
31 | /web/uploads/fields/*.JPG
32 | /web/uploads/fields/*.GIF
33 | /web/uploads/seeds/*.PNG
34 | /web/uploads/seeds/*.JPG
35 | /web/uploads/seeds/*.GIF
36 | # Swap
37 | [._]*.s[a-v][a-z]
38 | [._]*.sw[a-p]
39 | [._]s[a-v][a-z]
40 | [._]sw[a-p]
41 |
42 | # Session
43 | Session.vim
44 |
45 | # Temporary
46 | .netrwhist
47 | *~
48 | # Auto-generated tag files
49 | tags
50 |
51 | .DS_Store
52 | docker/**/Dockerfile
53 |
--------------------------------------------------------------------------------
/.editorconfig:
--------------------------------------------------------------------------------
1 | root = true
2 |
3 | [*]
4 | charset = utf-8
5 | end_of_line = lf
6 | insert_final_newline = true
7 | indent_style = space
8 | indent_size = 4
9 | trim_trailing_whitespace = true
10 |
11 | [*.md]
12 | trim_trailing_whitespace = false
13 |
--------------------------------------------------------------------------------
/.env-example:
--------------------------------------------------------------------------------
1 | #use 'en' for English and 'id' for Indonesia
2 | SYMFONY_LOCALE=en
3 |
4 | SYMFONY_SECRET=changewithyoursecretkey
5 | SYMFONY_ENV=dev
6 |
7 | #use '' instead of null if you want to empty the value
8 | SYMFONY_DB_HOST=127.0.0.1
9 | SYMFONY_DB_PORT=3306
10 | SYMFONY_DB_NAME=yourdatabasename
11 | SYMFONY_DB_USERNAME=yourdatabaseusername
12 | SYMFONY_DB_PASSWORD=yourdatabasepassword
13 |
14 | #use this default value if you don't have any mailer system
15 | SYMFONY_MAILER_TRANSPORT=smtp
16 | SYMFONY_MAILER_HOST=127.0.0.1
17 | SYMFONY_MAILER_USERNAME=admin
18 | SYMFONY_MAILER_PASSWORD=admin
19 | SYMFONY_MAILER_FROM_ADDRESS=youremail@yourdomain.com
20 | SYMFONY_MAILER_SENDER_NAME=yourname
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | /.web-server-pid
2 | /app/config/parameters.yml
3 | /build/
4 | /phpunit.xml
5 | /var/*
6 | !/var/cache
7 | /var/cache/*
8 | !var/cache/.gitkeep
9 | !/var/logs
10 | /var/logs/*
11 | !var/logs/.gitkeep
12 | !/var/sessions
13 | /var/sessions/*
14 | !var/sessions/.gitkeep
15 | !var/SymfonyRequirements.php
16 | /vendor/
17 | /web/bundles/
18 | /web/uploads/areas/*.png
19 | /web/uploads/areas/*.jpg
20 | /web/uploads/areas/*.gif
21 | /web/uploads/fields/*.png
22 | /web/uploads/fields/*.jpg
23 | /web/uploads/fields/*.gif
24 | /web/uploads/seeds/*.png
25 | /web/uploads/seeds/*.jpg
26 | /web/uploads/seeds/*.gif
27 | /web/uploads/areas/*.PNG
28 | /web/uploads/areas/*.JPG
29 | /web/uploads/areas/*.GIF
30 | /web/uploads/fields/*.PNG
31 | /web/uploads/fields/*.JPG
32 | /web/uploads/fields/*.GIF
33 | /web/uploads/seeds/*.PNG
34 | /web/uploads/seeds/*.JPG
35 | /web/uploads/seeds/*.GIF
36 | /web/vendor/*
37 | .env
38 | composer.phar
39 | # Swap
40 | [._]*.s[a-v][a-z]
41 | [._]*.sw[a-p]
42 | [._]s[a-v][a-z]
43 | [._]sw[a-p]
44 |
45 | # Session
46 | Session.vim
47 |
48 | # Temporary
49 | .netrwhist
50 | *~
51 | # Auto-generated tag files
52 | tags
53 |
54 | .DS_Store
55 |
56 | docker-compose.override.yml
57 | .vscode
58 |
--------------------------------------------------------------------------------
/.travis.yml:
--------------------------------------------------------------------------------
1 | language: php
2 |
3 | dist: trusty
4 |
5 | sudo: required
6 |
7 | env:
8 | global:
9 | SYMFONY_LOCALE=en
10 | SYMFONY_SECRET=xCqnuwqgU7h151
11 | SYMFONY_ENV=test
12 | SYMFONY_DB_HOST=127.0.0.1
13 | SYMFONY_DB_PORT=3306
14 | SYMFONY_DB_NAME=tania_test
15 | SYMFONY_DB_USERNAME=root
16 | SYMFONY_DB_PASSWORD=''
17 | SYMFONY_MAILER_TRANSPORT=smtp
18 | SYMFONY_MAILER_HOST=127.0.0.1
19 | SYMFONY_MAILER_USERNAME=admin
20 | SYMFONY_MAILER_PASSWORD=admin
21 | SYMFONY_MAILER_FROM_ADDRESS=youremail@yourdomain.com
22 | SYMFONY_MAILER_SENDER_NAME=yourname
23 |
24 | cache:
25 | directories:
26 | - $HOME/.composer/cache/files
27 |
28 | php:
29 | - '7.1'
30 |
31 | before_install:
32 | - mysql -e 'CREATE DATABASE tania_test'
33 |
34 | install:
35 | - composer install --no-interaction
36 | - php bin/console --no-interaction doctrine:migrations:migrate --env=test
37 | - php bin/console --no-interaction doctrine:fixtures:load -n --env=test
38 |
39 | script:
40 | - ./vendor/bin/phpunit
41 |
42 | after_success:
43 | - docker build -t tanibox/tania -f docker/app/Dockerfile --build-arg BUILD_DATE="$(date +%Y-%m-%d)" .
44 |
45 | branches:
46 | only:
47 | - development
48 |
49 | services:
50 | - mysql
51 |
--------------------------------------------------------------------------------
/CODE_OF_CONDUCT.md:
--------------------------------------------------------------------------------
1 | # Contributor Covenant Code of Conduct
2 |
3 | ## Our Pledge
4 |
5 | In the interest of fostering an open and welcoming environment, we as contributors and maintainers pledge to making participation in our project and our community a harassment-free experience for everyone, regardless of age, body size, disability, ethnicity, gender identity and expression, level of experience, nationality, personal appearance, race, religion, or sexual identity and orientation.
6 |
7 | ## Our Standards
8 |
9 | Examples of behavior that contributes to creating a positive environment include:
10 |
11 | * Using welcoming and inclusive language
12 | * Being respectful of differing viewpoints and experiences
13 | * Gracefully accepting constructive criticism
14 | * Focusing on what is best for the community
15 | * Showing empathy towards other community members
16 |
17 | Examples of unacceptable behavior by participants include:
18 |
19 | * The use of sexualized language or imagery and unwelcome sexual attention or advances
20 | * Trolling, insulting/derogatory comments, and personal or political attacks
21 | * Public or private harassment
22 | * Publishing others' private information, such as a physical or electronic address, without explicit permission
23 | * Other conduct which could reasonably be considered inappropriate in a professional setting
24 |
25 | ## Our Responsibilities
26 |
27 | Project maintainers are responsible for clarifying the standards of acceptable behavior and are expected to take appropriate and fair corrective action in response to any instances of unacceptable behavior.
28 |
29 | Project maintainers have the right and responsibility to remove, edit, or reject comments, commits, code, wiki edits, issues, and other contributions that are not aligned to this Code of Conduct, or to ban temporarily or permanently any contributor for other behaviors that they deem inappropriate, threatening, offensive, or harmful.
30 |
31 | ## Scope
32 |
33 | This Code of Conduct applies both within project spaces and in public spaces when an individual is representing the project or its community. Examples of representing a project or community include using an official project e-mail address, posting via an official social media account, or acting as an appointed representative at an online or offline event. Representation of a project may be further defined and clarified by project maintainers.
34 |
35 | ## Enforcement
36 |
37 | Instances of abusive, harassing, or otherwise unacceptable behavior may be reported by contacting the project team at [asep@tanibox.com](mailto:asep@tanibox.com). All complaints will be reviewed and investigated and will result in a response that is deemed necessary and appropriate to the circumstances. The project team is obligated to maintain confidentiality with regard to the reporter of an incident. Further details of specific enforcement policies may be posted separately.
38 |
39 | Project maintainers who do not follow or enforce the Code of Conduct in good faith may face temporary or permanent repercussions as determined by other members of the project's leadership.
40 |
41 | ## Attribution
42 |
43 | This Code of Conduct is adapted from the [Contributor Covenant][homepage], version 1.4, available at [http://contributor-covenant.org/version/1/4][version]
44 |
45 | [homepage]: http://contributor-covenant.org
46 | [version]: http://contributor-covenant.org/version/1/4/
47 |
--------------------------------------------------------------------------------
/CONTRIBUTING.md:
--------------------------------------------------------------------------------
1 | # Contributing to Tania
2 |
3 | Hello fellow contributors, we would like to thank you for taking the time to contribute!
4 |
5 | The following is a set of guidelines for contributing to Tania, which are hosted in the [Tanibox Organization](https://github.com/tanibox) on GitHub. These are mostly guidelines, not rules. Use your best judgment, and feel free to propose changes to this document in a pull request.
6 |
7 | #### Table Of Contents
8 |
9 | [Code of Conduct](#code-of-conduct)
10 |
11 | [What should I know before I get started?](#what-should-i-know-before-i-get-started)
12 |
13 | [How Can I Contribute?](#how-can-i-contribute)
14 | * [Reporting Bugs](#reporting-bugs)
15 | * [Suggesting Enhancements](#suggesting-enhancements)
16 | * [Pull Requests](#pull-requests)
17 |
18 | ## Code of Conduct
19 |
20 | This project and everyone participating in it is governed by the [Tania Code of Conduct](CODE_OF_CONDUCT.md). By participating, you are expected to uphold this code. Please report unacceptable behavior to [asep@tanibox.com](mailto:asep@tanibox.com).
21 |
22 | ## What should I know before I get started?
23 |
24 | Always use English to communicate. Don't be shy with your English because nobody is perfect.
25 |
26 | ## How Can I Contribute?
27 |
28 | ### Reporting Bugs
29 |
30 | To report bugs, you can use [our JIRA issue tracker](https://gettania.atlassian.net). Explain the detail about how can you get the bug, your environment, or anything that can help the maintainers to reproduce it.
31 |
32 | ### Suggesting Enhancements
33 |
34 | You can use [our JIRA issue tracker](https://gettania.atlassian.net) to suggest your enhancements proposal. We encourage you to join to our [Gitter](https://gitter.im/taniafarm/Lobby) also if you want to discuss your enhancements directly with the maintainers.
35 |
36 | ### Pull Requests
37 |
38 | Never ever send your pull requests to the `master` branch. Always send it to the `development` branch. Don't forget to give a clear PR subject and explain what are you changing on the description.
39 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # End Official Support and Maintenance for Tania PHP
2 |
3 | As the rewrite of Tania from PHP to Go is completed, and we have released the new Tania project to the public repository. The support for Tania PHP is ended. Please, check the new project at [tania-core](https://github.com/Tanibox/tania-core).
4 |
5 | 
6 |
7 | [](https://gitter.im/taniafarm/Lobby)
8 | [](https://travis-ci.org/Tanibox/tania)
9 |
10 | Tania is a free and open source farming management system for everyone. You can manage your growing areas, reservoirs, farm tasks, inventories, and the crop growing progress.
11 |
12 | It is developed on top of Symfony PHP web framework.
13 |
14 | To get the stable release, you can checkout to the `master` branch or from the [release tab](https://github.com/Tanibox/tania/releases).
15 |
16 | ## Screenshots
17 |
18 | 
19 |
20 | ## Requirements
21 |
22 | - PHP >= 7.0
23 | - MySQL >= 5.6
24 | - Composer (you can install from [getcomposer.org](http://getcomposer.org))
25 |
26 | ## General installation steps
27 |
28 | First, clone this project:
29 |
30 | ```
31 | git clone git@github.com:Tanibox/tania.git
32 | cd tania
33 | ```
34 |
35 | Second, setup your database and mailer parameters in `/.env`. You can duplicate and rename the `/.env-example` file.
36 |
37 | Third, setup the web application:
38 |
39 | ```
40 | curl -sS https://getcomposer.org/installer | php
41 | php composer.phar install
42 | ```
43 |
44 | Fourth, setup the database tables:
45 |
46 | ```
47 | php bin/console --no-interaction doctrine:migrations:migrate
48 | ```
49 |
50 | Fifth, create user:
51 |
52 | ```
53 | php bin/console fos:user:create {{user}} {{email}} {{password}}
54 | ```
55 |
56 | The last, you can run Tania in development mode (on your PC or laptop) by using this command:
57 |
58 | ```
59 | php bin/console server:run
60 | ```
61 |
62 | Tania will run on `http://localhost:8000`.
63 |
64 | You can also run Tania in production mode (on your server) by referring to this [Symfony documentation](http://symfony.com/doc/current/setup/web_server_configuration.html).
65 |
66 | Done! You can start to use Tania.
67 |
68 | ## Questions and issues
69 |
70 | You can use [our JIRA issue tracker](https://gettania.atlassian.net) for bug reporting, feature request, and general feedback.
71 |
72 | ## Maintainers
73 |
74 | Current maintainers:
75 |
76 | - Asep Bagja Priandana - [Linkedin](https://www.linkedin.com/in/asepbagja/)
77 | - Retno Ika Safitri - [Linkedin](https://www.linkedin.com/in/retnoika/)
78 | - Didiet Noor - [Linkedin](https://www.linkedin.com/in/didiet/)
79 |
80 | If you are interested in being a core contributor to this project, please drop me an email at __asep@tanibox.com__.
81 |
82 | ## License
83 |
84 | Tania is available under Apache 2.0 open source license.
85 |
--------------------------------------------------------------------------------
/app/.htaccess:
--------------------------------------------------------------------------------
1 |
2 | Require all denied
3 |
4 |
5 | Order deny,allow
6 | Deny from all
7 |
8 |
--------------------------------------------------------------------------------
/app/AppCache.php:
--------------------------------------------------------------------------------
1 | load($envFile);
16 | }
17 |
18 | $bundles = [
19 | new Symfony\Bundle\FrameworkBundle\FrameworkBundle(),
20 | new Symfony\Bundle\SecurityBundle\SecurityBundle(),
21 | new Symfony\Bundle\TwigBundle\TwigBundle(),
22 | new Symfony\Bundle\MonologBundle\MonologBundle(),
23 | new Symfony\Bundle\SwiftmailerBundle\SwiftmailerBundle(),
24 | new Doctrine\Bundle\DoctrineBundle\DoctrineBundle(),
25 | new Doctrine\Bundle\MigrationsBundle\DoctrineMigrationsBundle(),
26 | new Sensio\Bundle\FrameworkExtraBundle\SensioFrameworkExtraBundle(),
27 | new Vich\UploaderBundle\VichUploaderBundle(),
28 | new FOS\UserBundle\FOSUserBundle(),
29 | new AppBundle\AppBundle(),
30 | ];
31 |
32 | if (in_array($this->getEnvironment(), ['dev', 'test'], true)) {
33 | $bundles[] = new Doctrine\Bundle\FixturesBundle\DoctrineFixturesBundle();
34 | $bundles[] = new Symfony\Bundle\DebugBundle\DebugBundle();
35 | $bundles[] = new Symfony\Bundle\WebProfilerBundle\WebProfilerBundle();
36 | $bundles[] = new Sensio\Bundle\DistributionBundle\SensioDistributionBundle();
37 |
38 | if ('dev' === $this->getEnvironment()) {
39 | $bundles[] = new Sensio\Bundle\GeneratorBundle\SensioGeneratorBundle();
40 | $bundles[] = new Symfony\Bundle\WebServerBundle\WebServerBundle();
41 | }
42 | }
43 |
44 | return $bundles;
45 | }
46 |
47 | public function getRootDir()
48 | {
49 | return __DIR__;
50 | }
51 |
52 | public function getCacheDir()
53 | {
54 | return dirname(__DIR__).'/var/cache/'.$this->getEnvironment();
55 | }
56 |
57 | public function getLogDir()
58 | {
59 | return dirname(__DIR__).'/var/logs';
60 | }
61 |
62 | public function registerContainerConfiguration(LoaderInterface $loader)
63 | {
64 | $loader->load($this->getRootDir().'/config/config_'.$this->getEnvironment().'.yml');
65 | }
66 | }
67 |
--------------------------------------------------------------------------------
/app/DoctrineMigrations/Version20170701083839.php:
--------------------------------------------------------------------------------
1 | abortIf($this->connection->getDatabasePlatform()->getName() !== 'mysql', 'Migration can only be executed safely on \'mysql\'.');
20 |
21 | $this->addSql("INSERT INTO `seed_categories` (`id`, `name`, `slug`, `description`, `updated_at`, `created_at`) VALUES
22 | (1, 'Herb', 'herb', NULL, NULL, NOW()),
23 | (2, 'Vegetable', 'vegetable', NULL, NULL, NOW()),
24 | (3, 'Sprout/Microgreens', 'sprout-microgreens', NULL, NULL, NOW()),
25 | (4, 'Fruit', 'fruit', NULL, NULL, NOW()),
26 | (5, 'Tubber', 'tubber', NULL, NULL, NOW()),
27 | (6, 'Flower', 'flower', NULL, NULL, NOW()),
28 | (7, 'Other', 'other', NULL, NULL, NOW());");
29 | }
30 |
31 | /**
32 | * @param Schema $schema
33 | */
34 | public function down(Schema $schema)
35 | {
36 | // this down() migration is auto-generated, please modify it to your needs
37 | $this->abortIf($this->connection->getDatabasePlatform()->getName() !== 'mysql', 'Migration can only be executed safely on \'mysql\'.');
38 |
39 | $this->addSql('TRUNCATE TABLE `seed_categories`;');
40 | }
41 | }
42 |
--------------------------------------------------------------------------------
/app/DoctrineMigrations/Version20170907000538.php:
--------------------------------------------------------------------------------
1 | abortIf($this->connection->getDatabasePlatform()->getName() !== 'mysql', 'Migration can only be executed safely on \'mysql\'.');
20 |
21 | $this->addSql('ALTER TABLE plants DROP seedling_amount');
22 | }
23 |
24 | /**
25 | * @param Schema $schema
26 | */
27 | public function down(Schema $schema)
28 | {
29 | // this down() migration is auto-generated, please modify it to your needs
30 | $this->abortIf($this->connection->getDatabasePlatform()->getName() !== 'mysql', 'Migration can only be executed safely on \'mysql\'.');
31 |
32 | $this->addSql('ALTER TABLE plants ADD seedling_amount INT NOT NULL');
33 | }
34 | }
35 |
--------------------------------------------------------------------------------
/app/DoctrineMigrations/Version20170914142257.php:
--------------------------------------------------------------------------------
1 | abortIf($this->connection->getDatabasePlatform()->getName() !== 'mysql', 'Migration can only be executed safely on \'mysql\'.');
20 |
21 | $this->addSql('ALTER TABLE areas ADD field_id INT DEFAULT NULL');
22 | $this->addSql('ALTER TABLE areas ADD CONSTRAINT FK_58B0B25C443707B0 FOREIGN KEY (field_id) REFERENCES fields (id)');
23 | $this->addSql('CREATE INDEX IDX_58B0B25C443707B0 ON areas (field_id)');
24 | }
25 |
26 | /**
27 | * @param Schema $schema
28 | */
29 | public function down(Schema $schema)
30 | {
31 | // this down() migration is auto-generated, please modify it to your needs
32 | $this->abortIf($this->connection->getDatabasePlatform()->getName() !== 'mysql', 'Migration can only be executed safely on \'mysql\'.');
33 |
34 | $this->addSql('ALTER TABLE areas DROP FOREIGN KEY FK_58B0B25C443707B0');
35 | $this->addSql('DROP INDEX IDX_58B0B25C443707B0 ON areas');
36 | $this->addSql('ALTER TABLE areas DROP field_id');
37 | }
38 | }
39 |
--------------------------------------------------------------------------------
/app/DoctrineMigrations/Version20170915083636.php:
--------------------------------------------------------------------------------
1 | abortIf($this->connection->getDatabasePlatform()->getName() !== 'mysql', 'Migration can only be executed safely on \'mysql\'.');
20 |
21 | $this->addSql('ALTER TABLE tasks ADD field_id INT DEFAULT NULL');
22 | $this->addSql('ALTER TABLE tasks ADD CONSTRAINT FK_50586597443707B0 FOREIGN KEY (field_id) REFERENCES fields (id)');
23 | $this->addSql('CREATE INDEX IDX_50586597443707B0 ON tasks (field_id)');
24 | }
25 |
26 | /**
27 | * @param Schema $schema
28 | */
29 | public function down(Schema $schema)
30 | {
31 | // this down() migration is auto-generated, please modify it to your needs
32 | $this->abortIf($this->connection->getDatabasePlatform()->getName() !== 'mysql', 'Migration can only be executed safely on \'mysql\'.');
33 |
34 | $this->addSql('ALTER TABLE tasks DROP FOREIGN KEY FK_50586597443707B0');
35 | $this->addSql('DROP INDEX IDX_50586597443707B0 ON tasks');
36 | $this->addSql('ALTER TABLE tasks DROP field_id');
37 | }
38 | }
39 |
--------------------------------------------------------------------------------
/app/DoctrineMigrations/Version20170918155155.php:
--------------------------------------------------------------------------------
1 | abortIf($this->connection->getDatabasePlatform()->getName() !== 'mysql', 'Migration can only be executed safely on \'mysql\'.');
20 |
21 | $this->addSql('CREATE TABLE areasdevices (id INT AUTO_INCREMENT NOT NULL, area_id INT DEFAULT NULL, device_id INT DEFAULT NULL, updated_at DATETIME DEFAULT NULL, created_at DATETIME NOT NULL, INDEX IDX_BC0E507EBD0F409C (area_id), INDEX IDX_BC0E507E94A4C7D4 (device_id), PRIMARY KEY(id)) DEFAULT CHARACTER SET utf8 COLLATE utf8_unicode_ci ENGINE = InnoDB');
22 | $this->addSql('CREATE TABLE devices (id INT AUTO_INCREMENT NOT NULL, field_id INT DEFAULT NULL, name VARCHAR(100) NOT NULL, description LONGTEXT DEFAULT NULL, device_type INT NOT NULL, updated_at DATETIME DEFAULT NULL, created_at DATETIME NOT NULL, INDEX IDX_11074E9A443707B0 (field_id), PRIMARY KEY(id)) DEFAULT CHARACTER SET utf8 COLLATE utf8_unicode_ci ENGINE = InnoDB');
23 | $this->addSql('ALTER TABLE areasdevices ADD CONSTRAINT FK_BC0E507EBD0F409C FOREIGN KEY (area_id) REFERENCES areas (id)');
24 | $this->addSql('ALTER TABLE areasdevices ADD CONSTRAINT FK_BC0E507E94A4C7D4 FOREIGN KEY (device_id) REFERENCES devices (id)');
25 | $this->addSql('ALTER TABLE devices ADD CONSTRAINT FK_11074E9A443707B0 FOREIGN KEY (field_id) REFERENCES fields (id)');
26 | }
27 |
28 | /**
29 | * @param Schema $schema
30 | */
31 | public function down(Schema $schema)
32 | {
33 | // this down() migration is auto-generated, please modify it to your needs
34 | $this->abortIf($this->connection->getDatabasePlatform()->getName() !== 'mysql', 'Migration can only be executed safely on \'mysql\'.');
35 |
36 | $this->addSql('ALTER TABLE areasdevices DROP FOREIGN KEY FK_BC0E507E94A4C7D4');
37 | $this->addSql('DROP TABLE areasdevices');
38 | $this->addSql('DROP TABLE devices');
39 | }
40 | }
41 |
--------------------------------------------------------------------------------
/app/DoctrineMigrations/Version20170930124648.php:
--------------------------------------------------------------------------------
1 | abortIf($this->connection->getDatabasePlatform()->getName() !== 'mysql', 'Migration can only be executed safely on \'mysql\'.');
20 |
21 | $this->addSql('CREATE TABLE resources (id INT AUTO_INCREMENT NOT NULL, type VARCHAR(100) NOT NULL, data_type VARCHAR(100) NOT NULL, unit VARCHAR(100) NOT NULL, updated_at DATETIME DEFAULT NULL, created_at DATETIME NOT NULL, PRIMARY KEY(id)) DEFAULT CHARACTER SET utf8 COLLATE utf8_unicode_ci ENGINE = InnoDB');
22 | $this->addSql('CREATE TABLE resourcesdevices (id INT AUTO_INCREMENT NOT NULL, device_id INT DEFAULT NULL, resource_id INT DEFAULT NULL, name VARCHAR(100) NOT NULL, description LONGTEXT DEFAULT NULL, rid VARCHAR(100) NOT NULL, updated_at DATETIME DEFAULT NULL, created_at DATETIME NOT NULL, INDEX IDX_E27EDE6B94A4C7D4 (device_id), INDEX IDX_E27EDE6B89329D25 (resource_id), PRIMARY KEY(id)) DEFAULT CHARACTER SET utf8 COLLATE utf8_unicode_ci ENGINE = InnoDB');
23 | $this->addSql('ALTER TABLE resourcesdevices ADD CONSTRAINT FK_E27EDE6B94A4C7D4 FOREIGN KEY (device_id) REFERENCES devices (id)');
24 | $this->addSql('ALTER TABLE resourcesdevices ADD CONSTRAINT FK_E27EDE6B89329D25 FOREIGN KEY (resource_id) REFERENCES resources (id)');
25 | }
26 |
27 | /**
28 | * @param Schema $schema
29 | */
30 | public function down(Schema $schema)
31 | {
32 | // this down() migration is auto-generated, please modify it to your needs
33 | $this->abortIf($this->connection->getDatabasePlatform()->getName() !== 'mysql', 'Migration can only be executed safely on \'mysql\'.');
34 |
35 | $this->addSql('ALTER TABLE resourcesdevices DROP FOREIGN KEY FK_E27EDE6B89329D25');
36 | $this->addSql('DROP TABLE resources');
37 | $this->addSql('DROP TABLE resourcesdevices');
38 | }
39 | }
40 |
--------------------------------------------------------------------------------
/app/DoctrineMigrations/Version20170930171444.php:
--------------------------------------------------------------------------------
1 | abortIf($this->connection->getDatabasePlatform()->getName() !== 'mysql', 'Migration can only be executed safely on \'mysql\'.');
20 |
21 | $this->addSql('ALTER TABLE resourcesdevices ADD data_type VARCHAR(20) NOT NULL, ADD unit VARCHAR(20) NOT NULL');
22 | }
23 |
24 | /**
25 | * @param Schema $schema
26 | */
27 | public function down(Schema $schema)
28 | {
29 | // this down() migration is auto-generated, please modify it to your needs
30 | $this->abortIf($this->connection->getDatabasePlatform()->getName() !== 'mysql', 'Migration can only be executed safely on \'mysql\'.');
31 |
32 | $this->addSql('ALTER TABLE resourcesdevices DROP data_type, DROP unit');
33 | }
34 | }
35 |
--------------------------------------------------------------------------------
/app/DoctrineMigrations/Version20171003083933.php:
--------------------------------------------------------------------------------
1 | abortIf($this->connection->getDatabasePlatform()->getName() !== 'mysql', 'Migration can only be executed safely on \'mysql\'.');
20 |
21 | $this->addSql('ALTER TABLE resources DROP data_type, DROP unit');
22 |
23 | // seeding resources data
24 | $this->addSql('INSERT INTO resources (`type`, `created_at`) VALUES ("Temperature", NOW())');
25 | $this->addSql('INSERT INTO resources (`type`, `created_at`) VALUES ("Humidity", NOW())');
26 | $this->addSql('INSERT INTO resources (`type`, `created_at`) VALUES ("Light", NOW())');
27 | $this->addSql('INSERT INTO resources (`type`, `created_at`) VALUES ("Nutrition", NOW())');
28 | $this->addSql('INSERT INTO resources (`type`, `created_at`) VALUES ("Moisture", NOW())');
29 | $this->addSql('INSERT INTO resources (`type`, `created_at`) VALUES ("pH", NOW())');
30 | $this->addSql('INSERT INTO resources (`type`, `created_at`) VALUES ("On/Off State", NOW())');
31 | $this->addSql('INSERT INTO resources (`type`, `created_at`) VALUES ("Custom", NOW())');
32 | }
33 |
34 | /**
35 | * @param Schema $schema
36 | */
37 | public function down(Schema $schema)
38 | {
39 | // this down() migration is auto-generated, please modify it to your needs
40 | $this->abortIf($this->connection->getDatabasePlatform()->getName() !== 'mysql', 'Migration can only be executed safely on \'mysql\'.');
41 |
42 | $this->addSql('ALTER TABLE resources ADD data_type VARCHAR(100) NOT NULL COLLATE utf8_unicode_ci, ADD unit VARCHAR(100) NOT NULL COLLATE utf8_unicode_ci');
43 |
44 | // emptying the table
45 | $this->addSql('TRUNCATE TABLE resources');
46 | }
47 | }
48 |
--------------------------------------------------------------------------------
/app/DoctrineMigrations/Version20171004065248.php:
--------------------------------------------------------------------------------
1 | abortIf($this->connection->getDatabasePlatform()->getName() !== 'mysql', 'Migration can only be executed safely on \'mysql\'.');
20 |
21 | $this->addSql('CREATE TABLE settings (id INT AUTO_INCREMENT NOT NULL, `key` VARCHAR(200) NOT NULL, value VARCHAR(200) NOT NULL, updated_at DATETIME DEFAULT NULL, PRIMARY KEY(id)) DEFAULT CHARACTER SET utf8 COLLATE utf8_unicode_ci ENGINE = InnoDB');
22 |
23 | // add the default key and value
24 | $this->addSql('INSERT INTO settings (`key`, `value`) VALUES ("mqtt_host", "broker.mqttdashboard.com")');
25 | $this->addSql('INSERT INTO settings (`key`, `value`) VALUES ("mqtt_port", "8000")');
26 | }
27 |
28 | /**
29 | * @param Schema $schema
30 | */
31 | public function down(Schema $schema)
32 | {
33 | // this down() migration is auto-generated, please modify it to your needs
34 | $this->abortIf($this->connection->getDatabasePlatform()->getName() !== 'mysql', 'Migration can only be executed safely on \'mysql\'.');
35 |
36 | $this->addSql('DROP TABLE settings');
37 | }
38 | }
39 |
--------------------------------------------------------------------------------
/app/Resources/FOSUserBundle/views/ChangePassword/change_password.html.twig:
--------------------------------------------------------------------------------
1 | {% extends "@FOSUser/layout.html.twig" %}
2 |
3 | {% block fos_user_content %}
4 | {% include "@FOSUser/ChangePassword/change_password_content.html.twig" %}
5 | {% endblock fos_user_content %}
6 |
--------------------------------------------------------------------------------
/app/Resources/FOSUserBundle/views/ChangePassword/change_password_content.html.twig:
--------------------------------------------------------------------------------
1 | {% trans_default_domain 'FOSUserBundle' %}
2 |
3 | {{ form_start(form, { 'action': path('fos_user_change_password'), 'attr': { 'class': 'fos_user_change_password' } }) }}
4 | {{ form_widget(form) }}
5 |
6 |
7 |
8 | {{ form_end(form) }}
9 |
--------------------------------------------------------------------------------
/app/Resources/FOSUserBundle/views/Profile/edit.html.twig:
--------------------------------------------------------------------------------
1 | {% extends 'base.html.twig' %}
2 |
3 | {% block body %}
4 |
5 | {% include 'navbar.html.twig' %}
6 | {% include 'sidebar.html.twig' %}
7 | {% include "@FOSUser/Profile/edit_content.html.twig" %}
8 |
9 | {% endblock body %}
10 |
--------------------------------------------------------------------------------
/app/Resources/FOSUserBundle/views/Profile/edit_content.html.twig:
--------------------------------------------------------------------------------
1 | {% trans_default_domain 'FOSUserBundle' %}
2 |
3 |
4 |
5 |
{% trans from "dashboard" %}User Profile{% endtrans %}
6 |
7 |
8 |
9 |
10 |
11 |
12 | {{ form_start(form, { 'action': path('fos_user_profile_edit'), 'attr': { 'class': 'fos_user_profile_edit' } }) }}
13 | {{ form_errors(form) }}
14 |
15 | {{ form_label(form.username) }}
16 | {{ form_errors(form.username) }}
17 | {{ form_widget(form.username, {'attr': {'class': 'form-control'}}) }}
18 |
19 |
20 | {{ form_label(form.email) }}
21 | {{ form_errors(form.email) }}
22 | {{ form_widget(form.email, {'attr': {'class': 'form-control'}}) }}
23 |
24 |
25 | {{ form_label(form.current_password) }}
26 | {{ form_errors(form.current_password) }}
27 | {{ form_widget(form.current_password, {'attr': {'class': 'form-control'}}) }}
28 |
29 |
34 | {{ form_end(form) }}
35 |
36 |
37 |
38 |
39 |
40 |
41 |
--------------------------------------------------------------------------------
/app/Resources/FOSUserBundle/views/Profile/show.html.twig:
--------------------------------------------------------------------------------
1 | {% extends "@FOSUser/layout.html.twig" %}
2 |
3 | {% block fos_user_content %}
4 | {% include "@FOSUser/Profile/show_content.html.twig" %}
5 | {% endblock fos_user_content %}
6 |
--------------------------------------------------------------------------------
/app/Resources/FOSUserBundle/views/Profile/show_content.html.twig:
--------------------------------------------------------------------------------
1 | {% trans_default_domain 'FOSUserBundle' %}
2 |
3 |
4 |
{{ 'profile.show.username'|trans }}: {{ user.username }}
5 |
{{ 'profile.show.email'|trans }}: {{ user.email }}
6 |
7 |
--------------------------------------------------------------------------------
/app/Resources/FOSUserBundle/views/Registration/check_email.html.twig:
--------------------------------------------------------------------------------
1 | {% extends "@FOSUser/layout.html.twig" %}
2 |
3 | {% trans_default_domain 'FOSUserBundle' %}
4 |
5 | {% block fos_user_content %}
6 | {{ 'registration.check_email'|trans({'%email%': user.email}) }}
7 | {% endblock fos_user_content %}
8 |
--------------------------------------------------------------------------------
/app/Resources/FOSUserBundle/views/Registration/confirmed.html.twig:
--------------------------------------------------------------------------------
1 | {% extends "@FOSUser/layout.html.twig" %}
2 |
3 | {% trans_default_domain 'FOSUserBundle' %}
4 |
5 | {% block fos_user_content %}
6 | {{ 'registration.confirmed'|trans({'%username%': user.username}) }}
7 | {% if targetUrl %}
8 | {{ 'registration.back'|trans }}
9 | {% endif %}
10 | {% endblock fos_user_content %}
11 |
--------------------------------------------------------------------------------
/app/Resources/FOSUserBundle/views/Registration/email.txt.twig:
--------------------------------------------------------------------------------
1 | {% trans_default_domain 'FOSUserBundle' %}
2 | {% block subject %}
3 | {%- autoescape false -%}
4 | {{ 'registration.email.subject'|trans({'%username%': user.username, '%confirmationUrl%': confirmationUrl}) }}
5 | {%- endautoescape -%}
6 | {% endblock %}
7 |
8 | {% block body_text %}
9 | {% autoescape false %}
10 | {{ 'registration.email.message'|trans({'%username%': user.username, '%confirmationUrl%': confirmationUrl}) }}
11 | {% endautoescape %}
12 | {% endblock %}
13 | {% block body_html %}{% endblock %}
14 |
--------------------------------------------------------------------------------
/app/Resources/FOSUserBundle/views/Registration/register.html.twig:
--------------------------------------------------------------------------------
1 | {% extends "@FOSUser/layout.html.twig" %}
2 |
3 | {% block fos_user_content %}
4 | {% include "@FOSUser/Registration/register_content.html.twig" %}
5 | {% endblock fos_user_content %}
6 |
--------------------------------------------------------------------------------
/app/Resources/FOSUserBundle/views/Registration/register_content.html.twig:
--------------------------------------------------------------------------------
1 | {% trans_default_domain 'FOSUserBundle' %}
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
{% trans from "dashboard" %}MANAGE FARMS EASIER & SMARTER{% endtrans %}
10 |
{% trans from "dashboard" %}This impressive and modern farm management application will help you to manage the operations of your farm in a more intuitive, collaborative, and efficient way.{% endtrans %}
11 |
12 |
31 |
32 |
33 |
34 |
35 |
36 |
37 |
38 |
--------------------------------------------------------------------------------
/app/Resources/FOSUserBundle/views/Resetting/check_email.html.twig:
--------------------------------------------------------------------------------
1 | {% extends "@FOSUser/layout.html.twig" %}
2 |
3 | {% trans_default_domain 'FOSUserBundle' %}
4 |
5 | {% block fos_user_content %}
6 |
7 |
8 |
9 |
10 |
11 |
12 |
{% trans from "dashboard" %}MANAGE FARMS EASIER & SMARTER{% endtrans %}
13 |
{% trans from "dashboard" %}This impressive and modern farm management application will help you to manage the operations of your farm in a more intuitive, collaborative, and efficient way.{% endtrans %}
14 |
15 |
20 |
21 |
22 |
23 |
24 |
25 |
26 |
27 | {% endblock %}
28 |
--------------------------------------------------------------------------------
/app/Resources/FOSUserBundle/views/Resetting/email.txt.twig:
--------------------------------------------------------------------------------
1 | {% trans_default_domain 'FOSUserBundle' %}
2 | {% block subject %}
3 | {%- autoescape false -%}
4 | {{ 'resetting.email.subject'|trans({'%username%': user.username}) }}
5 | {%- endautoescape -%}
6 | {% endblock %}
7 |
8 | {% block body_text %}
9 | {% autoescape false %}
10 | {{ 'resetting.email.message'|trans({'%username%': user.username, '%confirmationUrl%': confirmationUrl}) }}
11 | {% endautoescape %}
12 | {% endblock %}
13 | {% block body_html %}{% endblock %}
14 |
--------------------------------------------------------------------------------
/app/Resources/FOSUserBundle/views/Resetting/request.html.twig:
--------------------------------------------------------------------------------
1 | {% extends "@FOSUser/layout.html.twig" %}
2 |
3 | {% block fos_user_content %}
4 | {% include "@FOSUser/Resetting/request_content.html.twig" %}
5 | {% endblock fos_user_content %}
6 |
--------------------------------------------------------------------------------
/app/Resources/FOSUserBundle/views/Resetting/request_content.html.twig:
--------------------------------------------------------------------------------
1 | {% trans_default_domain 'FOSUserBundle' %}
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
{% trans from "dashboard" %}MANAGE FARMS EASIER & SMARTER{% endtrans %}
10 |
{% trans from "dashboard" %}This impressive and modern farm management application will help you to manage the operations of your farm in a more intuitive, collaborative, and efficient way.{% endtrans %}
11 |
12 |
24 |
25 |
26 |
27 |
28 |
29 |
30 |
31 |
--------------------------------------------------------------------------------
/app/Resources/FOSUserBundle/views/Resetting/reset.html.twig:
--------------------------------------------------------------------------------
1 | {% extends "@FOSUser/layout.html.twig" %}
2 |
3 | {% block fos_user_content %}
4 | {% include "@FOSUser/Resetting/reset_content.html.twig" %}
5 | {% endblock fos_user_content %}
6 |
--------------------------------------------------------------------------------
/app/Resources/FOSUserBundle/views/Resetting/reset_content.html.twig:
--------------------------------------------------------------------------------
1 | {% trans_default_domain 'FOSUserBundle' %}
2 |
3 | {{ form_start(form, { 'action': path('fos_user_resetting_reset', {'token': token}), 'attr': { 'class': 'fos_user_resetting_reset' } }) }}
4 | {{ form_widget(form) }}
5 |
6 |
7 |
8 | {{ form_end(form) }}
9 |
--------------------------------------------------------------------------------
/app/Resources/FOSUserBundle/views/Security/login.html.twig:
--------------------------------------------------------------------------------
1 | {% extends "@FOSUser/layout.html.twig" %}
2 |
3 | {% block fos_user_content %}
4 | {{ include('@FOSUser/Security/login_content.html.twig') }}
5 | {% endblock fos_user_content %}
6 |
--------------------------------------------------------------------------------
/app/Resources/FOSUserBundle/views/Security/login_content.html.twig:
--------------------------------------------------------------------------------
1 | {% trans_default_domain 'FOSUserBundle' %}
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
{% trans from "dashboard" %}MANAGE FARMS EASIER & SMARTER{% endtrans %}
10 |
{% trans from "dashboard" %}This impressive and modern farm management application will help you to manage the operations of your farm in a more intuitive, collaborative, and efficient way.{% endtrans %}
11 |
12 |
44 |
45 |
46 |
47 |
48 |
49 |
50 |
--------------------------------------------------------------------------------
/app/Resources/FOSUserBundle/views/layout.html.twig:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 | {% block title %}TANIA{% endblock %}
12 |
13 | {% block stylesheets %}
14 |
15 |
16 |
17 | {% endblock %}
18 |
19 |
23 |
24 |
25 | {% block fos_user_content %}{% endblock fos_user_content %}
26 |
27 | {% block javascripts %}{% endblock %}
28 |
29 |
--------------------------------------------------------------------------------
/app/Resources/views/area/index.html.twig:
--------------------------------------------------------------------------------
1 | {% extends 'base.html.twig' %}
2 |
3 | {% block body %}
4 | {% trans_default_domain "dashboard" %}
5 |
6 | {% include 'navbar.html.twig' %}
7 | {% include 'sidebar.html.twig' %}
8 |
9 |
10 |
11 |
{% trans %}Add Area{% endtrans %}
12 |
{% trans %}All Areas{% endtrans %}
13 |
14 |
15 |
16 | {% set index = 0 %}
17 | {% for area in areas %}
18 |
19 |
20 | {% if vich_uploader_asset(area, 'imageFile') %}
21 |
22 | {% endif %}
23 |
24 |
25 |
26 | {% if area.reservoir is not null %}
27 |
{{ area.reservoir.field.name }}
28 | {% endif %}
29 |
30 |
31 |
32 |
{% trans %}System{% endtrans %}
33 |
34 | {{ growingMethods[index] }}
35 |
36 |
37 |
38 |
{% trans %}Capacity{% endtrans %}
39 |
40 | {{ area.capacity }} {{ measurementUnits[index] }}
41 |
42 |
43 |
44 |
45 |
46 |
47 | {% set index = index + 1 %}
48 | {% endfor %}
49 |
50 |
51 |
52 | {% include 'right-sidebar.html.twig' %}
53 |
54 | {% endblock %}
--------------------------------------------------------------------------------
/app/Resources/views/base.html.twig:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 | {% block title %}Tania{% endblock %}
12 |
13 | {% block stylesheets %}
14 |
15 |
16 |
17 |
18 |
19 |
20 | {% endblock %}
21 |
22 |
26 |
27 |
28 |
29 |
30 | {% block body %}{% endblock %}
31 |
32 | {% block javascripts %}
33 |
34 |
35 |
36 |
37 |
38 | {% if classActive == "fields_create" %}
39 |
40 |
41 | {% elseif classActive == "fields_show" %}
42 |
43 |
44 | {% elseif classActive == "areas_create" or classActive == "areas_edit" %}
45 |
46 | {% endif %}
47 |
48 |
53 | {% endblock %}
54 |
55 |
56 |
--------------------------------------------------------------------------------
/app/Resources/views/device/areas.html.twig:
--------------------------------------------------------------------------------
1 | {% extends 'base.html.twig' %}
2 |
3 | {% block body %}
4 | {% trans_default_domain "dashboard" %}
5 |
6 | {% include 'navbar.html.twig' %}
7 | {% include 'sidebar.html.twig' %}
8 |
9 |
10 |
{% trans %}Areas for{% endtrans %} {{ device.name }}
11 |
12 |
13 |
14 |
15 |
16 |
17 | {{ form_start(form, {'attr': {'class': 'group-border-dashed', 'style': 'border-radius: 0px;'}}) }}
18 | {{ form_errors(form) }}
19 |
20 | {{ form_label(form.area, 'Area', {'label_attr': {'class': 'control-label'}}) }}
21 | {{ form_errors(form.area) }}
22 | {{ form_widget(form.area, {'attr': {'class': 'form-control'}}) }}
23 |
24 |
30 | {{form_end(form)}}
31 |
32 |
33 |
34 |
62 |
63 |
64 |
65 | {% include 'right-sidebar.html.twig' %}
66 |
67 | {% endblock %}
--------------------------------------------------------------------------------
/app/Resources/views/device/create.html.twig:
--------------------------------------------------------------------------------
1 | {% extends 'base.html.twig' %}
2 |
3 | {% block body %}
4 | {% trans_default_domain "dashboard" %}
5 |
6 | {% include 'navbar.html.twig' %}
7 | {% include 'sidebar.html.twig' %}
8 |
9 |
10 |
11 |
{% trans %}Add New Device{% endtrans %}
12 |
13 |
14 |
15 |
16 |
17 |
18 | {{ form_start(form, {'attr': {'class': 'form-horizontal group-border-dashed', 'style': 'border-radius: 0px;'}}) }}
19 | {{ form_errors(form) }}
20 |
27 |
34 |
41 |
47 | {{form_end(form)}}
48 |
49 |
50 |
51 |
52 |
53 |
54 |
55 | {% include 'right-sidebar.html.twig' %}
56 |
57 | {% endblock %}
--------------------------------------------------------------------------------
/app/Resources/views/device/index.html.twig:
--------------------------------------------------------------------------------
1 | {% extends 'base.html.twig' %}
2 |
3 | {% block body %}
4 | {% trans_default_domain "dashboard" %}
5 |
6 | {% include 'navbar.html.twig' %}
7 | {% include 'sidebar.html.twig' %}
8 |
9 |
10 |
11 |
{% trans %}Add New Device{% endtrans %}
12 |
{% trans %}All Devices{% endtrans %}
13 |
14 |
57 |
58 |
59 | {% include 'right-sidebar.html.twig' %}
60 |
61 | {% endblock %}
--------------------------------------------------------------------------------
/app/Resources/views/device/show.html.twig:
--------------------------------------------------------------------------------
1 | {% extends 'base.html.twig' %}
2 |
3 | {% block body %}
4 | {% trans_default_domain "dashboard" %}
5 |
6 | {% include 'navbar.html.twig' %}
7 | {% include 'sidebar.html.twig' %}
8 |
9 |
10 |
{% trans %}Detail Information for{% endtrans %} {{ device.name }}
11 |
12 |
13 |
14 |
15 |
Device Type: {{ device.deviceType }}
16 |
Description: {{ device.description }}
17 |
18 |
19 |
20 |
21 |
Resources:
22 |
23 | {% for resourceDevice in resourcesDevices %}
24 |
25 | Name: {{ resourceDevice.name }}
26 | Description: {{ resourceDevice.description }}
27 | MQTT Channel (RID): tania/{{ resourceDevice.rid }}
28 | Data Type: {{ resourceDevice.dataType }}
29 | Unit: {{ resourceDevice.unit }}
30 |
31 | {% endfor %}
32 |
33 |
34 |
35 |
Areas:
36 |
37 |
38 | {% for areaDevice in areasDevices %}
39 |
40 | {{ areaDevice.area.name }}
41 |
42 | {% endfor %}
43 |
44 |
45 |
46 |
47 |
48 |
49 | {% include 'right-sidebar.html.twig' %}
50 |
51 | {% endblock %}
--------------------------------------------------------------------------------
/app/Resources/views/field/add.html.twig:
--------------------------------------------------------------------------------
1 | {% extends 'base.html.twig' %}
2 |
3 | {% block body %}
4 | {% trans_default_domain "dashboard" %}
5 |
6 | {% include 'navbar.html.twig' %}
7 | {% include 'sidebar.html.twig' %}
8 |
9 |
10 |
11 |
{% trans %}Add New Farm{% endtrans %}
12 |
13 |
14 |
15 |
16 |
17 |
18 | {{ form_start(form) }}
19 | {{ form_errors(form) }}
20 |
21 | {{ form_label(form.name, 'Name (0/50 chars)', {'label_attr': {'id': 'label_field_name'}}) }}
22 | {{ form_errors(form.name) }}
23 | {{ form_widget(form.name, {'attr': {'class': 'form-control'}}) }}
24 |
25 |
39 |
40 | {{ form_label(form.description) }}
41 | {{ form_errors(form.description) }}
42 | {{ form_widget(form.description, {'attr': {'class': 'form-control'}}) }}
43 |
44 |
45 | {{ form_label(form.imageFile) }}
46 | {{ form_errors(form.imageFile) }}
47 | {{ form_widget(form.imageFile, {'attr': {'class': 'form-control'}}) }}
48 |
49 |
55 | {{form_end(form)}}
56 |
57 |
58 |
59 |
62 |
63 |
64 |
65 | {% include 'right-sidebar.html.twig' %}
66 |
67 |
68 | {% endblock %}
--------------------------------------------------------------------------------
/app/Resources/views/field/index.html.twig:
--------------------------------------------------------------------------------
1 | {% extends 'base.html.twig' %}
2 |
3 | {% block body %}
4 | {% trans_default_domain "dashboard" %}
5 |
6 | {% include 'navbar.html.twig' %}
7 | {% include 'sidebar.html.twig' %}
8 |
9 |
10 |
11 |
12 | {% trans %}Add New Farm{% endtrans %}
13 |
14 |
{% trans %}All Farms/Greenhouses{% endtrans %}
15 |
16 |
17 |
18 | {% for field in fields %}
19 |
20 |
21 | {% if vich_uploader_asset(field, 'imageFile') %}
22 |
23 | {% endif %}
24 |
29 |
30 |
31 | {% endfor %}
32 |
33 |
34 |
35 | {% include 'right-sidebar.html.twig' %}
36 |
37 | {% endblock %}
--------------------------------------------------------------------------------
/app/Resources/views/navbar.html.twig:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/app/Resources/views/plant/harvest.html.twig:
--------------------------------------------------------------------------------
1 | {% extends 'base.html.twig' %}
2 |
3 | {% block body %}
4 | {% trans_default_domain "dashboard" %}
5 |
6 | {% include 'navbar.html.twig' %}
7 | {% include 'sidebar.html.twig' %}
8 |
9 |
10 |
11 |
{% trans %}Action for{% endtrans %} {{ plant.seed.name }}
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 | {% for message in app.flashes('notice') %}
20 |
21 | {{ message }}
22 |
23 | {% endfor %}
24 | {{ form_start(form) }}
25 |
26 | Seedling date
27 |
28 |
29 |
30 | {{ form_label(form.action, 'Harvest or Dispose') }}
31 | {{ form_widget(form.action) }}
32 |
33 |
34 | {{ form_label(form.note) }}
35 | {{ form_errors(form.note) }}
36 | {{ form_widget(form.note, {'attr': {'class': 'form-control'}}) }}
37 |
38 |
44 | {{ form_end(form) }}
45 |
46 |
47 |
48 |
49 |
50 |
51 | {% include 'right-sidebar.html.twig' %}
52 |
53 | {% endblock %}
--------------------------------------------------------------------------------
/app/Resources/views/plant/index.html.twig:
--------------------------------------------------------------------------------
1 | {% extends 'base.html.twig' %}
2 |
3 | {% block body %}
4 | {% trans_default_domain "dashboard" %}
5 |
6 | {% include 'navbar.html.twig' %}
7 | {% include 'sidebar.html.twig' %}
8 |
9 |
10 |
11 |
{% trans %}Add plant{% endtrans %}
12 |
{% trans %}Plant Varieties{% endtrans %}
13 |
14 |
15 |
16 |
17 | {% for plant in plants %}
18 |
19 |
20 | {% if vich_uploader_asset(plant['seed'], 'imageFile', 'AppBundle\\Entity\\Seed') %}
21 |
22 | {% endif %}
23 |
24 |
25 |
26 |
{{ plant['seed_category'] }}
27 |
28 |
29 |
30 |
{% trans %}Amount{% endtrans %}
31 |
{{ plant['seedling_total'] }}
32 |
33 |
34 |
{% trans %}Total Seedling Area{% endtrans %}
35 |
{{ plant['area_count'] }}
36 |
37 |
38 |
39 |
40 |
41 | {% endfor %}
42 |
43 |
44 |
45 | {% include 'right-sidebar.html.twig' %}
46 |
47 | {% endblock %}
--------------------------------------------------------------------------------
/app/Resources/views/plant/show.html.twig:
--------------------------------------------------------------------------------
1 | {% extends 'base.html.twig' %}
2 |
3 | {% block body %}
4 | {% trans_default_domain "dashboard" %}
5 |
6 | {% include 'navbar.html.twig' %}
7 | {% include 'sidebar.html.twig' %}
8 |
9 |
10 |
11 |
14 |
{{ plants[0].seed.name }}
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 | {% trans %}Total area{% endtrans %}: {{ totalArea }}
24 |
25 |
26 |
27 |
28 |
29 | {% trans %}Age (days){% endtrans %}
30 | {% trans %}Area{% endtrans %}
31 | {% trans %}Amount{% endtrans %}
32 | {% trans %}Status{% endtrans %}
33 | {% trans %}Action{% endtrans %}
34 |
35 |
36 |
37 | {% for plant in plants %}
38 |
39 | {{ plant.seedlingDate }}
40 | {{ plant.area.name }}
41 | {{ plant.areaCapacity }}
42 |
43 | {% if plant.action == 'harvest' %}
44 | {% trans %}Harvested{% endtrans %}
45 | {% elseif plant.action == 'dispose' %}
46 | {% trans %}Disposed{% endtrans %}
47 | {% endif %}
48 |
49 |
50 | {% trans %}Harvest{% endtrans %}/{% trans %}Dispose{% endtrans %}
51 |
52 |
53 | {% endfor %}
54 |
55 |
56 |
57 |
58 |
59 |
60 |
61 |
62 |
63 | {% include 'right-sidebar.html.twig' %}
64 |
65 | {% endblock %}
--------------------------------------------------------------------------------
/app/Resources/views/reservoir/show.html.twig:
--------------------------------------------------------------------------------
1 | {% extends 'base.html.twig' %}
2 |
3 | {% block body %}
4 | {% trans_default_domain "dashboard" %}
5 |
6 | {% include 'navbar.html.twig' %}
7 | {% include 'sidebar.html.twig' %}
8 |
9 |
10 |
11 |
{% trans %}Edit Reservoir{% endtrans %}: {{ reservoir.name }}
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 | {{ form_start(form) }}
20 | {{ form_errors(form) }}
21 |
35 |
49 |
55 | {{ form_end(form) }}
56 |
57 |
58 |
59 |
60 |
61 |
62 | {% include 'right-sidebar.html.twig' %}
63 |
64 | {% endblock %}
--------------------------------------------------------------------------------
/app/Resources/views/right-sidebar.html.twig:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/app/Resources/views/settings/index.html.twig:
--------------------------------------------------------------------------------
1 | {% extends 'base.html.twig' %}
2 |
3 | {% block body %}
4 | {% trans_default_domain "dashboard" %}
5 |
6 | {% include 'navbar.html.twig' %}
7 | {% include 'sidebar.html.twig' %}
8 |
9 |
10 |
11 |
Tania {% trans %}Preferences{% endtrans %}
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 | {% trans %}Internet of Things{% endtrans %}
21 |
22 |
23 | {{ form_start(form, {'attr': {'class': 'form-horizontal group-border-dashed'}}) }}
24 | {{ form_errors(form) }}
25 |
32 |
39 |
40 |
41 | {{ form_widget(form.save, {'attr': {'class': 'btn btn-primary btn-lg'}}) }}
42 |
43 |
44 | {{ form_end(form) }}
45 |
46 |
47 |
48 |
49 |
50 |
51 | {% include 'right-sidebar.html.twig' %}
52 |
53 | {% endblock %}
--------------------------------------------------------------------------------
/app/Resources/views/task/index.html.twig:
--------------------------------------------------------------------------------
1 | {% extends 'base.html.twig' %}
2 |
3 | {% block body %}
4 | {% trans_default_domain "dashboard" %}
5 |
6 | {% include 'navbar.html.twig' %}
7 | {% include 'sidebar.html.twig' %}
8 |
9 |
10 |
11 |
{% trans %}Add New{% endtrans %}
12 |
{% trans %}Farm Tasks{% endtrans %}
13 |
14 |
15 |
16 |
17 |
18 |
19 |
{% trans %}All Tasks{% endtrans %}
20 |
21 |
22 |
23 |
24 | {% trans %}Category{% endtrans %}
25 | {% trans %}Task{% endtrans %}
26 | {% trans %}Notes{% endtrans %}
27 | {% trans %}Due Date{% endtrans %}
28 | {% trans %}Level of Importance{% endtrans %}
29 | {% trans %}Is it done?{% endtrans %}
30 |
31 |
32 |
33 | {% for task in tasks %}
34 |
35 | {{ task.category }}
36 | {{ task.name }}
37 | {{ task.notes }}
38 | {{ task.dueDate|date('d F Y h:i')}}
39 |
40 | {{ task.urgencyLevel }}
41 |
42 | {% if task.isDone == 0 %} {% trans %}No{% endtrans %} {% elseif task.isDone == 1 %} {% trans %}Yes{% endtrans %} {% endif %}
43 |
44 | {% endfor %}
45 |
46 |
47 |
48 |
49 |
50 |
51 |
52 |
53 | {% include 'right-sidebar.html.twig' %}
54 |
55 | {% endblock %}
56 |
--------------------------------------------------------------------------------
/app/config/config_dev.yml:
--------------------------------------------------------------------------------
1 | imports:
2 | - { resource: config.yml }
3 |
4 | framework:
5 | router:
6 | resource: '%kernel.project_dir%/app/config/routing_dev.yml'
7 | strict_requirements: true
8 | profiler: { only_exceptions: false }
9 |
10 | web_profiler:
11 | toolbar: true
12 | intercept_redirects: false
13 |
14 | monolog:
15 | handlers:
16 | main:
17 | type: stream
18 | path: '/tmp/stdout'
19 | level: debug
20 | channels: ['!event']
21 | console:
22 | type: console
23 | process_psr_3_messages: false
24 | channels: ['!event', '!doctrine', '!console']
25 | # To follow logs in real time, execute the following command:
26 | # `bin/console server:log -vv`
27 | server_log:
28 | type: server_log
29 | process_psr_3_messages: false
30 | host: 127.0.0.1:9911
31 | # uncomment to get logging in your browser
32 | # you may have to allow bigger header sizes in your Web server configuration
33 | #firephp:
34 | # type: firephp
35 | # level: info
36 | #chromephp:
37 | # type: chromephp
38 | # level: info
39 |
40 | #swiftmailer:
41 | # delivery_addresses: ['me@example.com']
42 |
--------------------------------------------------------------------------------
/app/config/config_prod.yml:
--------------------------------------------------------------------------------
1 | imports:
2 | - { resource: config.yml }
3 |
4 | #doctrine:
5 | # orm:
6 | # metadata_cache_driver: apc
7 | # result_cache_driver: apc
8 | # query_cache_driver: apc
9 |
10 | monolog:
11 | handlers:
12 | main:
13 | type: fingers_crossed
14 | action_level: error
15 | handler: nested
16 | nested:
17 | type: stream
18 | path: '/tmp/stdout'
19 | level: debug
20 | console:
21 | type: console
22 | process_psr_3_messages: false
23 |
--------------------------------------------------------------------------------
/app/config/config_test.yml:
--------------------------------------------------------------------------------
1 | imports:
2 | - { resource: config_dev.yml }
3 |
4 | doctrine:
5 | dbal:
6 | host: '%env(SYMFONY_DB_HOST)%'
7 | port: '%env(SYMFONY_DB_PORT)%'
8 | dbname: '%env(SYMFONY_DB_NAME)%'
9 | user: '%env(SYMFONY_DB_USERNAME)%'
10 | password: '%env(SYMFONY_DB_PASSWORD)%'
11 |
12 | framework:
13 | test: ~
14 | session:
15 | storage_id: session.storage.mock_file
16 | profiler:
17 | collect: false
18 |
19 | security:
20 | firewalls:
21 | main:
22 | http_basic: ~
23 |
24 | web_profiler:
25 | toolbar: false
26 | intercept_redirects: false
27 |
28 | swiftmailer:
29 | disable_delivery: true
30 |
--------------------------------------------------------------------------------
/app/config/repository.yml:
--------------------------------------------------------------------------------
1 | services:
2 | app.repository.plant_repository:
3 | class: 'AppBundle\Repository\PlantRepository'
4 | arguments:
5 | - '@doctrine.orm.entity_manager'
6 | - 'AppBundle\Entity\Plant'
7 |
8 | app.repository.task_repository:
9 | class: 'AppBundle\Repository\TaskRepository'
10 | arguments:
11 | - '@doctrine.orm.entity_manager'
12 | - 'AppBundle\Entity\Task'
--------------------------------------------------------------------------------
/app/config/routing_dev.yml:
--------------------------------------------------------------------------------
1 | _wdt:
2 | resource: '@WebProfilerBundle/Resources/config/routing/wdt.xml'
3 | prefix: /_wdt
4 |
5 | _profiler:
6 | resource: '@WebProfilerBundle/Resources/config/routing/profiler.xml'
7 | prefix: /_profiler
8 |
9 | _errors:
10 | resource: '@TwigBundle/Resources/config/routing/errors.xml'
11 | prefix: /_error
12 |
13 | _main:
14 | resource: routing.yml
15 |
--------------------------------------------------------------------------------
/app/config/security.yml:
--------------------------------------------------------------------------------
1 | # To get started with security, check out the documentation:
2 | # http://symfony.com/doc/current/security.html
3 | security:
4 | encoders:
5 | FOS\UserBundle\Model\UserInterface: bcrypt
6 |
7 | role_hierarchy:
8 | ROLE_ADMIN: ROLE_USER
9 | ROLE_SUPER_ADMIN: ROLE_ADMIN
10 |
11 | # http://symfony.com/doc/current/security.html#b-configuring-how-users-are-loaded
12 | providers:
13 | fos_userbundle:
14 | id: fos_user.user_provider.username
15 |
16 | firewalls:
17 | # disables authentication for assets and the profiler, adapt it according to your needs
18 | dev:
19 | pattern: ^/(_(profiler|wdt)|css|images|js)/
20 | security: false
21 |
22 | main:
23 | # activate different ways to authenticate
24 |
25 | # http://symfony.com/doc/current/security.html#a-configuring-how-your-users-will-authenticate
26 | #http_basic: ~
27 |
28 | # http://symfony.com/doc/current/cookbook/security/form_login_setup.html
29 | #form_login: ~
30 | pattern: ^/
31 | form_login:
32 | provider: fos_userbundle
33 | csrf_token_generator: security.csrf.token_manager
34 | # if you are using Symfony < 2.8, use the following config instead:
35 | # csrf_provider: form.csrf_provider
36 |
37 | logout: true
38 | anonymous: true
39 |
40 | access_control:
41 | - { path: ^/login$, role: IS_AUTHENTICATED_ANONYMOUSLY }
42 | - { path: ^/register, role: IS_AUTHENTICATED_ANONYMOUSLY }
43 | - { path: ^/resetting, role: IS_AUTHENTICATED_ANONYMOUSLY }
44 | - { path: ^/admin/, role: ROLE_ADMIN }
45 | - { path: ^/, role: ROLE_USER }
46 |
--------------------------------------------------------------------------------
/app/config/services.yml:
--------------------------------------------------------------------------------
1 | # Learn more about services, parameters and containers at
2 | # http://symfony.com/doc/current/service_container.html
3 | parameters:
4 | #parameter_name: value
5 |
6 | services:
7 | # default configuration for services in *this* file
8 | _defaults:
9 | # automatically injects dependencies in your services
10 | autowire: true
11 | # automatically registers your services as commands, event subscribers, etc.
12 | autoconfigure: true
13 | # this means you cannot fetch services directly from the container via $container->get()
14 | # if you need to do this, you can override this setting on individual services
15 | public: false
16 |
17 | # makes classes in src/AppBundle available to be used as services
18 | # this creates a service per class whose id is the fully-qualified class name
19 | AppBundle\:
20 | resource: '../../src/AppBundle/*'
21 | # you can exclude directories or files
22 | # but if a service is unused, it's removed anyway
23 | exclude: '../../src/AppBundle/{Entity,Repository}'
24 |
25 | # controllers are imported separately to make sure they're public
26 | # and have a tag that allows actions to type-hint services
27 | AppBundle\Controller\:
28 | resource: '../../src/AppBundle/Controller'
29 | public: true
30 | tags: ['controller.service_arguments']
31 |
32 | # add more services, or override services that need manual wiring
33 | # AppBundle\Service\ExampleService:
34 | # arguments:
35 | # $someArgument: 'some_value'
36 |
37 | app.form.registration:
38 | class: AppBundle\Form\RegistrationFormType
39 | tags:
40 | - { name: form.type, alias: app_user_registration }
--------------------------------------------------------------------------------
/bin/console:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env php
2 | getParameterOption(['--env', '-e'], getenv('SYMFONY_ENV') ?: 'dev');
20 | $debug = getenv('SYMFONY_DEBUG') !== '0' && !$input->hasParameterOption(['--no-debug', '']) && $env !== 'prod';
21 |
22 | if ($debug) {
23 | Debug::enable();
24 | }
25 |
26 | $kernel = new AppKernel($env, $debug);
27 | $application = new Application($kernel);
28 | $application->run($input);
29 |
--------------------------------------------------------------------------------
/bower.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "tania",
3 | "homepage": "https://github.com/Tanibox/tania",
4 | "description": "",
5 | "main": "",
6 | "license": "Apache License 2.0 (Apache-2.0)",
7 | "ignore": [
8 | "**/.*",
9 | "node_modules",
10 | "bower_components",
11 | "test",
12 | "tests"
13 | ],
14 | "dependencies": {
15 | "datetimepicker": "^2.5.4"
16 | }
17 | }
18 |
--------------------------------------------------------------------------------
/composer.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "tanibox/tania",
3 | "description": "Free and open source farming management system.",
4 | "license": "Apache-2.0",
5 | "type": "project",
6 | "autoload": {
7 | "psr-4": {
8 | "AppBundle\\": "src/AppBundle"
9 | },
10 | "classmap": [
11 | "app/AppKernel.php",
12 | "app/AppCache.php"
13 | ]
14 | },
15 | "autoload-dev": {
16 | "psr-4": {
17 | "Tests\\": "tests/"
18 | },
19 | "files": [
20 | "vendor/symfony/symfony/src/Symfony/Component/VarDumper/Resources/functions/dump.php"
21 | ]
22 | },
23 | "require": {
24 | "php": ">=7.0",
25 | "doctrine/doctrine-bundle": "^1.6",
26 | "doctrine/doctrine-migrations-bundle": "^1.2",
27 | "doctrine/orm": "^2.5",
28 | "friendsofsymfony/user-bundle": "~2.0",
29 | "incenteev/composer-parameter-handler": "^2.0",
30 | "sensio/distribution-bundle": "^5.0.19",
31 | "sensio/framework-extra-bundle": "^3.0.2",
32 | "symfony/monolog-bundle": "^3.1.0",
33 | "symfony/options-resolver": "^3.3",
34 | "symfony/polyfill-apcu": "^1.0",
35 | "symfony/swiftmailer-bundle": "^2.3.10",
36 | "symfony/symfony": "3.3.*",
37 | "symfony/translation": "^3.3",
38 | "symfony/var-dumper": "^3.3",
39 | "twig/twig": "^1.0||^2.0",
40 | "vich/uploader-bundle": "^1.4"
41 | },
42 | "require-dev": {
43 | "doctrine/doctrine-fixtures-bundle": "^2.3",
44 | "phpunit/phpunit": "6.2",
45 | "sensio/generator-bundle": "^3.0",
46 | "symfony/phpunit-bridge": "^3.0"
47 | },
48 | "scripts": {
49 | "symfony-scripts": [
50 | "Sensio\\Bundle\\DistributionBundle\\Composer\\ScriptHandler::buildBootstrap",
51 | "Sensio\\Bundle\\DistributionBundle\\Composer\\ScriptHandler::clearCache",
52 | "Sensio\\Bundle\\DistributionBundle\\Composer\\ScriptHandler::installAssets",
53 | "Sensio\\Bundle\\DistributionBundle\\Composer\\ScriptHandler::installRequirementsFile",
54 | "Sensio\\Bundle\\DistributionBundle\\Composer\\ScriptHandler::prepareDeploymentTarget"
55 | ],
56 | "post-install-cmd": [
57 | "@symfony-scripts"
58 | ],
59 | "post-update-cmd": [
60 | "@symfony-scripts"
61 | ]
62 | },
63 | "config": {
64 | "sort-packages": true
65 | },
66 | "extra": {
67 | "symfony-app-dir": "app",
68 | "symfony-bin-dir": "bin",
69 | "symfony-var-dir": "var",
70 | "symfony-web-dir": "web",
71 | "symfony-tests-dir": "tests",
72 | "symfony-assets-install": "relative"
73 | }
74 | }
75 |
--------------------------------------------------------------------------------
/docker-compose.dev.yml:
--------------------------------------------------------------------------------
1 |
2 | version: '2.2'
3 |
4 | services:
5 |
6 | app:
7 | image: tanibox/tania:latest
8 | build:
9 | dockerfile: docker/app/Dockerfile
10 | context: .
11 | environment:
12 | SYMFONY_LOCALE: en
13 | SYMFONY_SECRET: AugIVKlefKLzqJwlwY5S5YaW8Ui66fi8
14 | SYMFONY_ENV: dev
15 | SYMFONY_DB_HOST: db
16 | SYMFONY_DB_PORT: 3306
17 | SYMFONY_DB_NAME: tania
18 | SYMFONY_DB_USERNAME: tania
19 | SYMFONY_DB_PASSWORD: taniapass
20 | SYMFONY_MAILER_TRANSPORT: smtp
21 | SYMFONY_MAILER_HOST: 127.0.0.1
22 | SYMFONY_MAILER_USERNAME: admin
23 | SYMFONY_MAILER_PASSWORD: admin
24 | SYMFONY_MAILER_FROM_ADDRESS: youremail@yourdomain.com
25 | SYMFONY_MAILER_SENDER_NAME: yourname
26 | COMPOSER_ALLOW_SUPERUSER: 1
27 | ports:
28 | - "80:80"
29 | volumes:
30 | - '.:/var/www'
31 | - '$HOME/.composer:/var/www/.composer'
32 | db:
33 | image: 'mysql:5.6'
34 | environment:
35 | MYSQL_ROOT_PASSWORD: root
36 | MYSQL_DATABASE: tania
37 | MYSQL_USER: tania
38 | MYSQL_PASSWORD: taniapass
39 | ports:
40 | - "3306:3306"
41 |
--------------------------------------------------------------------------------
/docker-compose.yml:
--------------------------------------------------------------------------------
1 | version: '2.2'
2 |
3 | services:
4 | app:
5 | image: tanibox/tania:latest
6 |
7 |
--------------------------------------------------------------------------------
/docker/app/Dockerfile:
--------------------------------------------------------------------------------
1 | FROM tanibox/php7-fpm-nginx-supervisord
2 |
3 | MAINTAINER Didiet Noor
4 |
5 | ARG BUILD_DATE
6 |
7 | LABEL org.label-schema.build-date=$BUILD_DATE \
8 | org.label-schema.name="Tania Web Application" \
9 | org.label-schema.description="Build artifact for Tania" \
10 | org.label-schema.url="http://gettania.org/" \
11 | org.label-schema.vcs-ref=$VCS_REF \
12 | org.label-schema.vcs-url="https://github.com/Tanibox/tania.git" \
13 | org.label-schema.vendor="Tania" \
14 | org.label-schema.version="1.2-beta" \
15 | org.label-schema.schema-version="1.0"
16 |
17 | ADD . /var/www
18 | COPY ./docker/app/nginx.conf /etc/nginx/nginx.conf
19 | COPY ./docker/app/tania-entrypoint /usr/local/bin/
20 | VOLUME /var/www/var/cache
21 | WORKDIR /var/www
22 |
23 | EXPOSE 80
24 |
25 | RUN touch /var/www/.env \
26 | && COMPOSER_ALLOW_SUPERUSER=1 composer install --no-autoloader --no-scripts --no-dev
27 |
28 | ENTRYPOINT [ "/usr/local/bin/tania-entrypoint" ]
29 |
--------------------------------------------------------------------------------
/docker/app/nginx.conf:
--------------------------------------------------------------------------------
1 | user www-data;
2 | worker_processes 4;
3 | pid /run/nginx.pid;
4 | daemon off;
5 |
6 | events {
7 | worker_connections 2048;
8 | multi_accept on;
9 | use epoll;
10 | }
11 |
12 | http {
13 | server_tokens off;
14 | sendfile on;
15 | tcp_nopush on;
16 | tcp_nodelay on;
17 | keepalive_timeout 15;
18 | types_hash_max_size 2048;
19 | include /etc/nginx/mime.types;
20 | default_type application/octet-stream;
21 | access_log off;
22 | error_log off;
23 | gzip on;
24 | gzip_disable "msie6";
25 | open_file_cache max=100;
26 |
27 | server {
28 | root /var/www/web;
29 |
30 | location / {
31 | try_files $uri @rewriteapp;
32 | }
33 |
34 | location @rewriteapp {
35 | rewrite ^(.*)$ /app.php/$1 last;
36 | }
37 |
38 | location ~ ^/(app|app_dev|config)\.php(/|$) {
39 | fastcgi_pass unix:/var/run/php-fpm.sock;
40 | fastcgi_split_path_info ^(.+\.php)(/.*)$;
41 | include fastcgi_params;
42 | fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
43 | fastcgi_param HTTPS off;
44 | }
45 |
46 | error_log /dev/stdout info;
47 | access_log /dev/stdout;
48 | }
49 | }
50 |
--------------------------------------------------------------------------------
/docker/app/tania-entrypoint:
--------------------------------------------------------------------------------
1 | #!/bin/sh
2 | set -e
3 |
4 | composer install
5 |
6 | chown www-data:www-data -R /var/www/var/cache
7 | chown www-data:www-data -R /var/www/var/logs
8 | chown www-data:www-data -R /var/www/var/sessions
9 |
10 |
11 | if [ ! -d /tmp ]; then
12 | mkdir -p /tmp
13 | fi
14 |
15 | if [ ! -e /tmp/stdout ]; then
16 | mkfifo -m 666 /tmp/stdout
17 | fi
18 |
19 | cat <> /tmp/stdout 1>&2 &
20 |
21 |
22 | # Needed for Alpine
23 | /usr/bin/supervisord -n -c /etc/supervisord.conf
24 |
--------------------------------------------------------------------------------
/phpunit.xml.dist:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 | tests
18 |
19 |
20 |
21 |
22 |
23 | src
24 |
25 | src/*Bundle/Resources
26 | src/*/*Bundle/Resources
27 | src/*/Bundle/*Bundle/Resources
28 |
29 |
30 |
31 |
32 |
--------------------------------------------------------------------------------
/readme-assets/project-dashboard.jpg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/readme-assets/project-dashboard.jpg
--------------------------------------------------------------------------------
/readme-assets/project-logo.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/readme-assets/project-logo.png
--------------------------------------------------------------------------------
/src/.htaccess:
--------------------------------------------------------------------------------
1 |
2 | Require all denied
3 |
4 |
5 | Order deny,allow
6 | Deny from all
7 |
8 |
--------------------------------------------------------------------------------
/src/AppBundle/AppBundle.php:
--------------------------------------------------------------------------------
1 | getRepository('AppBundle:Field')->findAll();
19 |
20 | return $this->render('field/index.html.twig', array(
21 | 'fields' => $fields,
22 | 'classActive' => $_route,
23 | 'farms' => $fields
24 | ));
25 | }
26 |
27 | /**
28 | This method will render the new field submission form and handle the submission.
29 | */
30 | public function createAction(Request $request, EntityManagerInterface $em, $_route)
31 | {
32 | // for the right bar menu
33 | $fields = $em->getRepository('AppBundle:Field')->findAll();
34 |
35 | $field = new Field();
36 |
37 | $form = $this->createForm(FieldType::class, $field);
38 |
39 | $form->handleRequest($request);
40 |
41 | if ($form->isSubmitted() && $form->isValid()) {
42 | $field = $form->getData();
43 |
44 | // save to database here
45 | $field->setCreatedAt(new \DateTime('now'));
46 |
47 | $em->persist($field);
48 | $em->flush();
49 |
50 | // redirect to dashboard and set the session variable with the new id
51 | return $this->redirectToRoute('fields_session', array('id' => $field->getId()));
52 | }
53 |
54 | return $this->render('field/add.html.twig', array(
55 | 'form' => $form->createView(),
56 | 'classActive' => $_route,
57 | 'farms' => $fields
58 | ));
59 | }
60 |
61 | /**
62 | and handle the data update when necessary.
63 | */
64 | public function showAction($id, EntityManagerInterface $em, Request $request, $_route)
65 | {
66 | $field = $em->getRepository('AppBundle:Field')->find($id);
67 |
68 | $form = $this->createForm(FieldType::class, $field);
69 |
70 | $form->handleRequest($request);
71 |
72 | if ($form->isSubmitted() && $form->isValid()) {
73 | $field = $form->getData();
74 |
75 | // save to database here
76 | $field->setUpdatedAt(new \DateTime('now'));
77 |
78 | $em->flush();
79 |
80 | return $this->redirectToRoute('fields');
81 | }
82 |
83 | // for the right bar menu
84 | $fields = $em->getRepository('AppBundle:Field')->findAll();
85 |
86 | return $this->render('field/show.html.twig', array(
87 | 'form' => $form->createView(),
88 | 'classActive' => $_route,
89 | 'lat' => $field->getLat(),
90 | 'lng' => $field->getLng(),
91 | 'farms' => $fields
92 | ));
93 | }
94 |
95 | /**
96 | Set the current active farm for this session
97 | */
98 | public function sessionAction($id)
99 | {
100 | $this->get('session')->set('activeFarm', $id);
101 | return $this->redirectToRoute('dashboard');
102 | }
103 | }
104 |
--------------------------------------------------------------------------------
/src/AppBundle/Controller/InventoryController.php:
--------------------------------------------------------------------------------
1 | getRepository('AppBundle:Seed')->findAll();
16 |
17 | // for the right bar menu
18 | $fields = $em->getRepository('AppBundle:Field')->findAll();
19 |
20 | return $this->render('inventory/index.html.twig', array(
21 | 'seeds' => $seeds,
22 | 'classActive' => $_route,
23 | 'farms' => $fields
24 | ));
25 | }
26 |
27 | public function seedCreateAction(Request $request, EntityManagerInterface $em, $_route)
28 | {
29 | $seed = new Seed();
30 |
31 | $form = $this->createForm(SeedType::class, $seed);
32 |
33 | $form->handleRequest($request);
34 |
35 | if ($form->isSubmitted() && $form->isValid()) {
36 | $seed = $form->getData();
37 |
38 | // save to database here
39 | $seed->setCreatedAt(new \DateTime('now'));
40 |
41 | $em->persist($seed);
42 | $em->flush();
43 |
44 | return $this->redirectToRoute('inventories');
45 | }
46 |
47 | // for the right bar menu
48 | $fields = $em->getRepository('AppBundle:Field')->findAll();
49 |
50 | return $this->render('seed/create.html.twig', array(
51 | 'form' => $form->createView(),
52 | 'classActive' => $_route,
53 | 'farms' => $fields
54 | ));
55 | }
56 |
57 | public function seedEditAction($id, $_route, Request $request, EntityManagerInterface $em)
58 | {
59 | $seed = $em->getRepository('AppBundle:Seed')->find($id);
60 |
61 | $form = $this->createForm(SeedType::class, $seed);
62 |
63 | $form->handleRequest($request);
64 |
65 | if ($form->isSubmitted() && $form->isValid()) {
66 | $seed = $form->getData();
67 |
68 | // save to database here
69 | $seed->setUpdatedAt(new \DateTime('now'));
70 |
71 | $em->persist($seed);
72 | $em->flush();
73 |
74 | return $this->redirectToRoute('inventories');
75 | }
76 |
77 | // for the right bar menu
78 | $fields = $em->getRepository('AppBundle:Field')->findAll();
79 |
80 | return $this->render('seed/edit.html.twig', array(
81 | 'form' => $form->createView(),
82 | 'seed' => $seed,
83 | 'classActive' => $_route,
84 | 'farms' => $fields
85 | ));
86 | }
87 | }
88 |
--------------------------------------------------------------------------------
/src/AppBundle/Controller/ProfileController.php:
--------------------------------------------------------------------------------
1 | getUser();
23 | if (!is_object($user) || !$user instanceof UserInterface) {
24 | throw new AccessDeniedException('This user does not have access to this section.');
25 | }
26 |
27 | /** @var $dispatcher EventDispatcherInterface */
28 | $dispatcher = $this->get('event_dispatcher');
29 |
30 | $event = new GetResponseUserEvent($user, $request);
31 | $dispatcher->dispatch(FOSUserEvents::PROFILE_EDIT_INITIALIZE, $event);
32 |
33 | if (null !== $event->getResponse()) {
34 | return $event->getResponse();
35 | }
36 |
37 | /** @var $formFactory FactoryInterface */
38 | $formFactory = $this->get('fos_user.profile.form.factory');
39 |
40 | $form = $formFactory->createForm();
41 | $form->setData($user);
42 |
43 | $form->handleRequest($request);
44 |
45 | if ($form->isSubmitted() && $form->isValid()) {
46 | /** @var $userManager UserManagerInterface */
47 | $userManager = $this->get('fos_user.user_manager');
48 |
49 | $event = new FormEvent($form, $request);
50 | $dispatcher->dispatch(FOSUserEvents::PROFILE_EDIT_SUCCESS, $event);
51 |
52 | $userManager->updateUser($user);
53 |
54 | if (null === $response = $event->getResponse()) {
55 | $url = $this->generateUrl('fos_user_profile_show');
56 | $response = new RedirectResponse($url);
57 | }
58 |
59 | $dispatcher->dispatch(FOSUserEvents::PROFILE_EDIT_COMPLETED, new FilterUserResponseEvent($user, $request, $response));
60 |
61 | return $response;
62 | }
63 |
64 | return $this->render('@FOSUser/Profile/edit.html.twig', array(
65 | 'form' => $form->createView(),
66 | 'classActive' => 'fos_user_profile_edit'
67 | ));
68 | }
69 | }
70 |
--------------------------------------------------------------------------------
/src/AppBundle/Controller/RegistrationController.php:
--------------------------------------------------------------------------------
1 |
21 | * @author Christophe Coevoet
22 | */
23 | class RegistrationController extends BaseController
24 | {
25 | /**
26 | * @param Request $request
27 | *
28 | * @return Response
29 | */
30 | public function registerAction(Request $request)
31 | {
32 | /** @var $formFactory FactoryInterface */
33 | $formFactory = $this->get('fos_user.registration.form.factory');
34 | /** @var $userManager UserManagerInterface */
35 | $userManager = $this->get('fos_user.user_manager');
36 | /** @var $dispatcher EventDispatcherInterface */
37 | $dispatcher = $this->get('event_dispatcher');
38 |
39 | $user = $userManager->createUser();
40 | $user->setEnabled(true);
41 |
42 | $event = new GetResponseUserEvent($user, $request);
43 | $dispatcher->dispatch(FOSUserEvents::REGISTRATION_INITIALIZE, $event);
44 |
45 | if (null !== $event->getResponse()) {
46 | return $event->getResponse();
47 | }
48 |
49 | $form = $formFactory->createForm();
50 | $form->setData($user);
51 |
52 | $form->handleRequest($request);
53 |
54 | if ($form->isSubmitted()) {
55 | if ($form->isValid()) {
56 | $event = new FormEvent($form, $request);
57 | $dispatcher->dispatch(FOSUserEvents::REGISTRATION_SUCCESS, $event);
58 |
59 | $userManager->updateUser($user);
60 |
61 | if (null === $response = $event->getResponse()) {
62 | $url = $this->generateUrl('dashboard');
63 | $response = new RedirectResponse($url);
64 | }
65 |
66 | $dispatcher->dispatch(FOSUserEvents::REGISTRATION_COMPLETED, new FilterUserResponseEvent($user, $request, $response));
67 |
68 | return $response;
69 | }
70 |
71 | $event = new FormEvent($form, $request);
72 | $dispatcher->dispatch(FOSUserEvents::REGISTRATION_FAILURE, $event);
73 |
74 | if (null !== $response = $event->getResponse()) {
75 | return $response;
76 | }
77 | }
78 |
79 | return $this->render('@FOSUser/Registration/register.html.twig', array(
80 | 'form' => $form->createView(),
81 | ));
82 | }
83 | }
84 |
--------------------------------------------------------------------------------
/src/AppBundle/Controller/ReservoirController.php:
--------------------------------------------------------------------------------
1 | get('session')->get('activeFarm');
16 |
17 | $reservoir = new Reservoir();
18 | $reservoirs = $em->getRepository('AppBundle:Reservoir')->findByField($activeFarmId);
19 |
20 | $form = $this->createForm(ReservoirType::class, $reservoir);
21 | $form->handleRequest($request);
22 |
23 | if ($form->isSubmitted() && $form->isValid()) {
24 | $reservoir = $form->getData();
25 |
26 | // save to database here
27 | $reservoir->setCreatedAt(new \DateTime('now'));
28 |
29 | $em->persist($reservoir);
30 | $em->flush();
31 |
32 | return $this->redirectToRoute('reservoirs');
33 | }
34 |
35 | // for the right bar menu
36 | $fields = $em->getRepository('AppBundle:Field')->findAll();
37 |
38 | return $this->render('reservoir/index.html.twig', array(
39 | 'form' => $form->createView(),
40 | 'reservoirs' => $reservoirs,
41 | 'classActive' => $_route,
42 | 'farms' => $fields
43 | ));
44 | }
45 |
46 | public function showAction($id, $_route, EntityManagerInterface $em, Request $request)
47 | {
48 | $reservoir = $em->getRepository('AppBundle:Reservoir')->find($id);
49 |
50 | $form = $this->createForm(ReservoirType::class, $reservoir);
51 |
52 | $form->handleRequest($request);
53 |
54 | if ($form->isSubmitted() && $form->isValid()) {
55 | $reservoir = $form->getData();
56 |
57 | // save to database here
58 | $reservoir->setUpdatedAt(new \DateTime('now'));
59 |
60 | $em->flush();
61 |
62 | return $this->redirectToRoute('reservoirs');
63 | }
64 |
65 | // for the right bar menu
66 | $fields = $em->getRepository('AppBundle:Field')->findAll();
67 |
68 | return $this->render('reservoir/show.html.twig', array(
69 | 'form' => $form->createView(),
70 | 'reservoir' => $reservoir,
71 | 'classActive' => $_route,
72 | 'farms' => $fields
73 | ));
74 | }
75 | }
76 |
--------------------------------------------------------------------------------
/src/AppBundle/Controller/SettingsController.php:
--------------------------------------------------------------------------------
1 | getRepository('AppBundle:Setting')->findBy(array('key' => array('mqtt_host', 'mqtt_port')));
16 |
17 | $form = $this->createForm(SettingType::class, array('mqttHost' => $mqtt[0]->getValue(), 'mqttPort' => $mqtt[1]->getValue()));
18 | $form->handleRequest($request);
19 |
20 | if ($form->isSubmitted() && $form->isValid()) {
21 | $data = $form->getData();
22 |
23 | // save to database
24 | $mqttHost = $em->getRepository('AppBundle:Setting')->findOneBy(array('key' => 'mqtt_host'));
25 | $mqttHost->setValue($data['mqttHost']);
26 | $mqttHost->setUpdatedAt(new \DateTime('now'));
27 | $em->persist($mqttHost);
28 |
29 | $mqttPort = $em->getRepository('AppBundle:Setting')->findOneBy(array('key' => 'mqtt_port'));
30 | $mqttPort->setValue($data['mqttPort']);
31 | $mqttPort->setUpdatedAt(new \DateTime('now'));
32 | $em->persist($mqttPort);
33 |
34 | $em->flush();
35 |
36 | return $this->redirectToRoute('settings');
37 | }
38 |
39 | // for the right bar menu
40 | $fields = $em->getRepository('AppBundle:Field')->findAll();
41 |
42 | return $this->render('settings/index.html.twig', array(
43 | 'classActive' => $_route,
44 | 'farms' => $fields,
45 | 'form' => $form->createView()
46 | ));
47 | }
48 | }
--------------------------------------------------------------------------------
/src/AppBundle/Controller/TaskController.php:
--------------------------------------------------------------------------------
1 | get('session')->get('activeFarm');
16 |
17 | $tasks = $em->getRepository('AppBundle:Task')->findByField($activeFarmId);
18 |
19 | // for the right bar menu
20 | $fields = $em->getRepository('AppBundle:Field')->findAll();
21 |
22 | return $this->render('task/index.html.twig', array(
23 | 'tasks' => $tasks,
24 | 'classActive' => $_route,
25 | 'farms' => $fields
26 | ));
27 | }
28 |
29 | public function createAction(Request $request, EntityManagerInterface $em, $_route)
30 | {
31 | $activeFarmId = $this->get('session')->get('activeFarm');
32 |
33 | $task = new Task();
34 |
35 | $form = $this->createForm(TaskType::class, $task);
36 |
37 | $form->handleRequest($request);
38 |
39 | if ($form->isSubmitted() && $form->isValid()) {
40 | $task = $form->getData();
41 |
42 | // save to database here
43 | $field = $em->getRepository('AppBundle:Field')->findOneById($activeFarmId);
44 | $task->setField($field);
45 | $task->setCreatedAt(new \DateTime('now'));
46 |
47 | $em->persist($task);
48 | $em->flush();
49 |
50 | return $this->redirectToRoute('tasks');
51 | }
52 |
53 | // for the right bar menu
54 | $fields = $em->getRepository('AppBundle:Field')->findAll();
55 |
56 | return $this->render('task/create.html.twig', array(
57 | 'form' => $form->createView(),
58 | 'classActive' => $_route,
59 | 'farms' => $fields
60 | ));
61 | }
62 |
63 | public function showAction($id, Request $request, EntityManagerInterface $em, $_route)
64 | {
65 | $task = $em->getRepository('AppBundle:Task')->find($id);
66 |
67 | $form = $this->createForm(TaskType::class, $task);
68 |
69 | $form->handleRequest($request);
70 |
71 | if ($form->isSubmitted() && $form->isValid()) {
72 | $task = $form->getData();
73 |
74 | // save to database here
75 | $task->setUpdatedAt(new \DateTime('now'));
76 |
77 | $em->flush();
78 |
79 | return $this->redirectToRoute('tasks');
80 | }
81 |
82 | // for the right bar menu
83 | $fields = $em->getRepository('AppBundle:Field')->findAll();
84 |
85 | return $this->render('task/show.html.twig', array(
86 | 'form' => $form->createView(),
87 | 'classActive' => $_route,
88 | 'farms' => $fields
89 | ));
90 | }
91 | }
92 |
--------------------------------------------------------------------------------
/src/AppBundle/Data/CategoryMaster.php:
--------------------------------------------------------------------------------
1 | 'NFT',
11 | 2 => 'Drip Irrigation',
12 | 3 => 'Ebb and Flow',
13 | 4 => 'Soil/Organic',
14 | );
15 | }
16 |
17 | public static function areaUnits()
18 | {
19 | return array(
20 | 1 => 'Holes',
21 | 2 => 'Trays',
22 | );
23 | }
24 |
25 | public static function seedUnits()
26 | {
27 | return array(
28 | 1 => 'seeds',
29 | 2 => 'gr',
30 | 3 => 'kg',
31 | 4 => 'lbs',
32 | 5 => 'oz',
33 | );
34 | }
35 |
36 | public static function deviceType()
37 | {
38 | return array(
39 | 1 => 'Xiaomi Flora',
40 | 2 => 'Raspberry Pi',
41 | 3 => 'Arduino',
42 | 4 => 'ESP8266',
43 | 5 => 'Other'
44 | );
45 | }
46 | }
47 |
--------------------------------------------------------------------------------
/src/AppBundle/DataFixtures/ORM/LoadResourceData.php:
--------------------------------------------------------------------------------
1 | setType('Temperature');
14 | $resource->setCreatedAt(new \DateTime('now'));
15 | $manager->persist($resource);
16 |
17 | $resource = new Resource();
18 | $resource->setType('Humidity');
19 | $resource->setCreatedAt(new \DateTime('now'));
20 | $manager->persist($resource);
21 |
22 | $resource = new Resource();
23 | $resource->setType('Light');
24 | $resource->setCreatedAt(new \DateTime('now'));
25 | $manager->persist($resource);
26 |
27 | $resource = new Resource();
28 | $resource->setType('Nutrition');
29 | $resource->setCreatedAt(new \DateTime('now'));
30 | $manager->persist($resource);
31 |
32 | $resource = new Resource();
33 | $resource->setType('Moisture');
34 | $resource->setCreatedAt(new \DateTime('now'));
35 | $manager->persist($resource);
36 |
37 | $resource = new Resource();
38 | $resource->setType('pH');
39 | $resource->setCreatedAt(new \DateTime('now'));
40 | $manager->persist($resource);
41 |
42 | $resource = new Resource();
43 | $resource->setType('On/Off State');
44 | $resource->setCreatedAt(new \DateTime('now'));
45 | $manager->persist($resource);
46 |
47 | $resource = new Resource();
48 | $resource->setType('Custom');
49 | $resource->setCreatedAt(new \DateTime('now'));
50 | $manager->persist($resource);
51 |
52 | $manager->flush();
53 | }
54 | }
--------------------------------------------------------------------------------
/src/AppBundle/DataFixtures/ORM/LoadSeedCategory.php:
--------------------------------------------------------------------------------
1 | setName('Herb');
14 | $category->setSlug('herb');
15 | $category->setCreatedAt(new \DateTime('now'));
16 | $manager->persist($category);
17 |
18 | $category = new SeedCategory();
19 | $category->setName('Vegetable');
20 | $category->setSlug('vegetable');
21 | $category->setCreatedAt(new \DateTime('now'));
22 | $manager->persist($category);
23 |
24 | $category = new SeedCategory();
25 | $category->setName('Sprout/Microgreens');
26 | $category->setSlug('sprout-microgreens');
27 | $category->setCreatedAt(new \DateTime('now'));
28 | $manager->persist($category);
29 |
30 | $category = new SeedCategory();
31 | $category->setName('Fruit');
32 | $category->setSlug('fruit');
33 | $category->setCreatedAt(new \DateTime('now'));
34 | $manager->persist($category);
35 |
36 | $category = new SeedCategory();
37 | $category->setName('Tubber');
38 | $category->setSlug('tubber');
39 | $category->setCreatedAt(new \DateTime('now'));
40 | $manager->persist($category);
41 |
42 | $category = new SeedCategory();
43 | $category->setName('Flower');
44 | $category->setSlug('flower');
45 | $category->setCreatedAt(new \DateTime('now'));
46 | $manager->persist($category);
47 |
48 | $category = new SeedCategory();
49 | $category->setName('Other');
50 | $category->setSlug('other');
51 | $category->setCreatedAt(new \DateTime('now'));
52 | $manager->persist($category);
53 |
54 | $manager->flush();
55 | }
56 | }
--------------------------------------------------------------------------------
/src/AppBundle/DataFixtures/ORM/LoadUserData.php:
--------------------------------------------------------------------------------
1 | container = $container;
20 | }
21 |
22 | public function load(ObjectManager $manager)
23 | {
24 | $userManager = $this->container->get('fos_user.user_manager');
25 |
26 | $email_exist = $userManager->findUserByEmail('test@test.id');
27 |
28 | // Check if the user exists to prevent Integrity constraint violation error in the insertion
29 | if($email_exist){
30 | return false;
31 | }
32 |
33 | $user = $userManager->createUser();
34 | $user->setUsername('testuser');
35 | $user->setEmail('test@test.id');
36 | $user->setEnabled(true);
37 | $user->setPlainPassword('test123');
38 |
39 | $userManager->updateUser($user);
40 | }
41 | }
--------------------------------------------------------------------------------
/src/AppBundle/DoctrineExtensions/Utils/AnyValue.php:
--------------------------------------------------------------------------------
1 | match(Lexer::T_IDENTIFIER);
17 | $parser->match(Lexer::T_OPEN_PARENTHESIS);
18 | $this->value = $parser->StringPrimary();
19 | $parser->match(Lexer::T_CLOSE_PARENTHESIS);
20 | }
21 |
22 | public function getSql(SqlWalker $sqlWalker)
23 | {
24 | return 'ANY_VALUE('.$this->value->dispatch($sqlWalker).')';
25 | }
26 | }
27 |
--------------------------------------------------------------------------------
/src/AppBundle/Entity/AreasDevices.php:
--------------------------------------------------------------------------------
1 | id;
58 | }
59 |
60 | /**
61 | * Set updatedAt
62 | *
63 | * @param \DateTime $updatedAt
64 | *
65 | * @return AreasDevices
66 | */
67 | public function setUpdatedAt($updatedAt)
68 | {
69 | $this->updatedAt = $updatedAt;
70 |
71 | return $this;
72 | }
73 |
74 | /**
75 | * Get updatedAt
76 | *
77 | * @return \DateTime
78 | */
79 | public function getUpdatedAt()
80 | {
81 | return $this->updatedAt;
82 | }
83 |
84 | /**
85 | * Set createdAt
86 | *
87 | * @param \DateTime $createdAt
88 | *
89 | * @return AreasDevices
90 | */
91 | public function setCreatedAt($createdAt)
92 | {
93 | $this->createdAt = $createdAt;
94 |
95 | return $this;
96 | }
97 |
98 | /**
99 | * Get createdAt
100 | *
101 | * @return \DateTime
102 | */
103 | public function getCreatedAt()
104 | {
105 | return $this->createdAt;
106 | }
107 |
108 | /**
109 | * Set area
110 | *
111 | * @param \AppBundle\Entity\Area $area
112 | *
113 | * @return AreasDevices
114 | */
115 | public function setArea(\AppBundle\Entity\Area $area = null)
116 | {
117 | $this->area = $area;
118 |
119 | return $this;
120 | }
121 |
122 | /**
123 | * Get area
124 | *
125 | * @return \AppBundle\Entity\Area
126 | */
127 | public function getArea()
128 | {
129 | return $this->area;
130 | }
131 |
132 | /**
133 | * Set device
134 | *
135 | * @param \AppBundle\Entity\Device $device
136 | *
137 | * @return AreasDevices
138 | */
139 | public function setDevice(\AppBundle\Entity\Device $device = null)
140 | {
141 | $this->device = $device;
142 |
143 | return $this;
144 | }
145 |
146 | /**
147 | * Get device
148 | *
149 | * @return \AppBundle\Entity\Device
150 | */
151 | public function getDevice()
152 | {
153 | return $this->device;
154 | }
155 | }
156 |
--------------------------------------------------------------------------------
/src/AppBundle/Entity/Setting.php:
--------------------------------------------------------------------------------
1 | id;
46 | }
47 |
48 | /**
49 | * Set key
50 | *
51 | * @param string $key
52 | *
53 | * @return Setting
54 | */
55 | public function setKey($key)
56 | {
57 | $this->key = $key;
58 |
59 | return $this;
60 | }
61 |
62 | /**
63 | * Get key
64 | *
65 | * @return string
66 | */
67 | public function getKey()
68 | {
69 | return $this->key;
70 | }
71 |
72 | /**
73 | * Set value
74 | *
75 | * @param string $value
76 | *
77 | * @return Setting
78 | */
79 | public function setValue($value)
80 | {
81 | $this->value = $value;
82 |
83 | return $this;
84 | }
85 |
86 | /**
87 | * Get value
88 | *
89 | * @return string
90 | */
91 | public function getValue()
92 | {
93 | return $this->value;
94 | }
95 |
96 | /**
97 | * Set updatedAt
98 | *
99 | * @param \DateTime $updatedAt
100 | *
101 | * @return Setting
102 | */
103 | public function setUpdatedAt($updatedAt)
104 | {
105 | $this->updatedAt = $updatedAt;
106 |
107 | return $this;
108 | }
109 |
110 | /**
111 | * Get updatedAt
112 | *
113 | * @return \DateTime
114 | */
115 | public function getUpdatedAt()
116 | {
117 | return $this->updatedAt;
118 | }
119 | }
120 |
--------------------------------------------------------------------------------
/src/AppBundle/Entity/User.php:
--------------------------------------------------------------------------------
1 | add('area', EntityType::class, array(
15 | 'class' => 'AppBundle:Area',
16 | 'choice_label' => 'name',
17 | 'required' => true,
18 | 'label' => 'Area Name',
19 | 'translation_domain' => 'dashboard'
20 | ))
21 | ->add('save', SubmitType::class, array(
22 | 'label' => 'Add Area',
23 | 'translation_domain' => 'dashboard'
24 | ));
25 | }
26 | }
--------------------------------------------------------------------------------
/src/AppBundle/Form/AreaType.php:
--------------------------------------------------------------------------------
1 | add('name', TextType::class, array(
21 | 'attr' => array('maxlength' => 50),
22 | 'label' => 'Name',
23 | 'translation_domain' => 'dashboard'))
24 | ->add('reservoir', EntityType::class, array(
25 | 'class' => 'AppBundle:Reservoir',
26 | 'choice_label' => 'name',
27 | 'required' => false,
28 | 'label' => 'Reservoir',
29 | 'translation_domain' => 'dashboard'
30 | ))
31 | ->add('growingMethod', ChoiceType::class, array(
32 | 'choices' => array(
33 | CategoryMaster::growingMethods()[1] => 1,
34 | CategoryMaster::growingMethods()[2] => 2,
35 | CategoryMaster::growingMethods()[3] => 3,
36 | CategoryMaster::growingMethods()[4] => 4,
37 | ),
38 | 'label' => 'Growing method',
39 | 'translation_domain' => 'dashboard'
40 | ))
41 | ->add('capacity', IntegerType::class, array(
42 | 'label' => 'Capacity',
43 | 'translation_domain' => 'dashboard'
44 | ))
45 | ->add('measurementUnit', ChoiceType::class, array(
46 | 'choices' => array(
47 | CategoryMaster::areaUnits()[1] => 1,
48 | CategoryMaster::areaUnits()[2] => 2,
49 | ),
50 | 'label' => 'Measurement unit',
51 | 'translation_domain' => 'dashboard'
52 | ))
53 | ->add('imageFile', VichImageType::class, array(
54 | 'required' => false,
55 | 'allow_delete' => true,
56 | 'image_uri' => true,
57 | 'download_uri' => true,
58 | 'label' => 'Image file',
59 | 'translation_domain' => 'dashboard'
60 | ))
61 | ->add('save', SubmitType::class, array(
62 | 'label' => 'Save',
63 | 'translation_domain' => 'dashboard'
64 | ));
65 | }
66 | }
67 |
--------------------------------------------------------------------------------
/src/AppBundle/Form/DeviceType.php:
--------------------------------------------------------------------------------
1 | add('name', TextType::class, array(
18 | 'attr' => array('maxlength' => 50),
19 | 'label' => 'Name',
20 | 'translation_domain' => 'dashboard'
21 | ))
22 | ->add('description', TextareaType::class, array(
23 | 'required' => false,
24 | 'label' => 'Description',
25 | 'translation_domain' => 'dashboard'
26 | ))
27 | ->add('deviceType', ChoiceType::class, array(
28 | 'choices' => array(
29 | CategoryMaster::deviceType()[1] => 1,
30 | CategoryMaster::deviceType()[2] => 2,
31 | CategoryMaster::deviceType()[3] => 3,
32 | CategoryMaster::deviceType()[4] => 4
33 | ),
34 | 'label' => 'Device type',
35 | 'required' => true,
36 | 'translation_domain' => 'dashboard'
37 | ))
38 | ->add('save', SubmitType::class, array(
39 | 'label' => 'Add Device',
40 | 'translation_domain' => 'dashboard'
41 | ));
42 | }
43 | }
--------------------------------------------------------------------------------
/src/AppBundle/Form/FieldType.php:
--------------------------------------------------------------------------------
1 | add('name', TextType::class, array(
19 | 'attr' => array('maxlength' => 50),
20 | 'label' => 'Name',
21 | 'translation_domain' => 'dashboard'))
22 | ->add('lat', NumberType::class, array(
23 | 'required' => false,
24 | 'scale' => 8,
25 | 'label' => 'Latitude',
26 | 'translation_domain' => 'dashboard'))
27 | ->add('lng', NumberType::class, array(
28 | 'required' => false,
29 | 'scale' => 8,
30 | 'label' => 'Longitude',
31 | 'translation_domain' => 'dashboard'))
32 | ->add('description', TextareaType::class, array(
33 | 'required' => false,
34 | 'label' => 'Description',
35 | 'translation_domain' => 'dashboard'))
36 | ->add('imageFile', VichImageType::class, array(
37 | 'required' => false,
38 | 'allow_delete' => true,
39 | 'image_uri' => true,
40 | 'download_uri' => true,
41 | 'label' => 'Image file',
42 | 'translation_domain' => 'dashboard'
43 | ))
44 | ->add('save', SubmitType::class, array(
45 | 'label' => 'Save',
46 | 'translation_domain' => 'dashboard'));
47 | }
48 | }
49 |
--------------------------------------------------------------------------------
/src/AppBundle/Form/PlantHarvestType.php:
--------------------------------------------------------------------------------
1 | add('action', ChoiceType::class, array(
17 | 'choices' => array('Harvest' => 'harvest', 'Dispose' => 'dispose'),
18 | 'expanded' => true,
19 | 'label' => 'Action',
20 | 'translation_domain' => 'dashboard'
21 | ))
22 | ->add('note', TextareaType::class, array(
23 | 'required' => false,
24 | 'label' => 'Note',
25 | 'translation_domain' => 'dashboard'))
26 | ->add('save', SubmitType::class, array(
27 | 'label' => 'Update',
28 | 'translation_domain' => 'dashboard'));
29 | }
30 | }
31 |
--------------------------------------------------------------------------------
/src/AppBundle/Form/PlantType.php:
--------------------------------------------------------------------------------
1 | setDefaults([
19 | 'entityManager' => null,
20 | ]);
21 | }
22 |
23 | public function buildForm(FormBuilderInterface $builder, array $options)
24 | {
25 | $builder
26 | ->add('area', EntityType::class, array(
27 | 'class' => 'AppBundle:Area',
28 | 'choice_label' => function ($area) use ($options) {
29 | // measurement unit for area capacity
30 | $unit = CategoryMaster::areaUnits()[$area->getMeasurementUnit()];
31 |
32 | // capacity left
33 | $areasInfo = $options['entityManager']->getRepository('AppBundle:Plant')->findBy(array('area' => $area->getId()));
34 | $usedArea = array_reduce($areasInfo, function ($carry, $item) {
35 | return $carry += $item->getAreaCapacity();
36 | });
37 | $areaLeft = $area->getCapacity() - $usedArea;
38 |
39 | return $area->getName().' (Capacities: '.$areaLeft.' '.$unit.' remaining)';
40 | },
41 | 'label' => 'Area',
42 | 'translation_domain' => 'dashboard'
43 | ))
44 | ->add('seed', EntityType::class, array(
45 | 'class' => 'AppBundle:Seed',
46 | 'choice_label' => function ($seed) use ($options) {
47 | // measurement unit for seed amount
48 | $unit = CategoryMaster::seedUnits()[$seed->getMeasurementUnit()];
49 |
50 | // seeds left
51 | $seedsInfo = $options['entityManager']->getRepository('AppBundle:Plant')->findBy(array('seed' => $seed->getId()));
52 |
53 | $usedSeed = array_reduce($seedsInfo, function ($carry, $item) {
54 | return $carry += $item->getAreaCapacity();
55 | });
56 | $seedLeft = $seed->getQuantity() - $usedSeed;
57 |
58 | return $seed->getName().' (Quantities: '.$seedLeft.' '.$unit.' remaining)';
59 | },
60 | 'label' => 'Seed',
61 | 'translation_domain' => 'dashboard'
62 | ))
63 | ->add('seedlingDate', DateType::class, array(
64 | 'years' => range(date('Y'), date('Y') - 1),
65 | 'widget' => 'single_text',
66 | 'label' => 'Seedling date',
67 | 'translation_domain' => 'dashboard'
68 | ))
69 | ->add('areaCapacity', IntegerType::class, array(
70 | 'label' => 'Area capacity',
71 | 'translation_domain' => 'dashboard'
72 | ))
73 | ->add('save', SubmitType::class, array(
74 | 'label' => 'Save',
75 | 'translation_domain' => 'dashboard'));
76 | }
77 | }
78 |
--------------------------------------------------------------------------------
/src/AppBundle/Form/RegistrationFormType.php:
--------------------------------------------------------------------------------
1 | add('plainPassword', LegacyFormHelper::getType('Symfony\Component\Form\Extension\Core\Type\RepeatedType'), array(
14 | 'type' => LegacyFormHelper::getType('Symfony\Component\Form\Extension\Core\Type\PasswordType'),
15 | 'options' => array('translation_domain' => 'FOSUserBundle', 'attr' => array('class' => 'form-control')),
16 | 'first_options' => array('label' => 'form.password'),
17 | 'second_options' => array('label' => 'form.password_confirmation'),
18 | 'invalid_message' => 'fos_user.password.mismatch',
19 | ));
20 | }
21 |
22 | public function getParent()
23 | {
24 | return 'FOS\UserBundle\Form\Type\RegistrationFormType';
25 | }
26 |
27 | public function getBlockPrefix()
28 | {
29 | return 'app_user_registration';
30 | }
31 |
32 | // For Symfony 2.x
33 | public function getName()
34 | {
35 | return $this->getBlockPrefix();
36 | }
37 | }
38 |
--------------------------------------------------------------------------------
/src/AppBundle/Form/ReservoirType.php:
--------------------------------------------------------------------------------
1 | add('name', TextType::class, array(
19 | 'label' => 'Name',
20 | 'translation_domain' => 'dashboard'
21 | ))
22 | ->add('field', EntityType::class, array(
23 | 'class' => 'AppBundle:Field',
24 | 'choice_label' => 'name',
25 | 'label' => 'Field',
26 | 'translation_domain' => 'dashboard'
27 | ))
28 | ->add('capacity', NumberType::class, array(
29 | 'scale' => 2,
30 | 'label' => 'Capacity',
31 | 'translation_domain' => 'dashboard'
32 | ))
33 | ->add('measurementUnit', ChoiceType::class, array(
34 | 'choices' => array(
35 | 'Litre' => 1,
36 | 'Gallon' => 2,
37 | ),
38 | 'label' => 'Measurement unit',
39 | 'translation_domain' => 'dashboard'
40 | ))
41 | ->add('save', SubmitType::class, array(
42 | 'label' => 'Save',
43 | 'translation_domain' => 'dashboard'
44 | ));
45 | }
46 | }
47 |
--------------------------------------------------------------------------------
/src/AppBundle/Form/ResourceDeviceType.php:
--------------------------------------------------------------------------------
1 | add('name', TextType::class, array(
20 | 'attr' => array('maxlength' => 50),
21 | 'label' => 'Name',
22 | 'translation_domain' => 'dashboard'
23 | ))
24 | ->add('description', TextareaType::class, array(
25 | 'required' => false,
26 | 'label' => 'Description',
27 | 'translation_domain' => 'dashboard'
28 | ))
29 | ->add('rid', TextType::class, array(
30 | 'attr' => array('maxlength' => 50),
31 | 'label' => 'Resource ID',
32 | 'translation_domain' => 'dashboard'
33 | ))
34 | ->add('resource', EntityType::class, array(
35 | 'class' => 'AppBundle:Resource',
36 | 'choice_label' => 'type',
37 | 'required' => true,
38 | 'label' => 'Resource Type',
39 | 'translation_domain' => 'dashboard'
40 | ))
41 | ->add('dataType', ChoiceType::class, array(
42 | 'choices' => array(
43 | 'Float' => 'Float',
44 | 'Integer' => 'Integer',
45 | 'Boolean' => 'Boolean',
46 | 'String' => 'String'
47 | ),
48 | 'label' => 'Data Type',
49 | 'translation_domain' => 'dashboard'
50 | ))
51 | ->add('unit', ChoiceType::class, array(
52 | 'choices' => array(
53 | 'Celcius' => 'Celcius',
54 | 'Fahrenheit' => 'Fahrenheit',
55 | 'uS/cm' => 'uS/cm',
56 | 'Lux' => 'Lux',
57 | '%' => '%',
58 | 'None' => 'None'
59 | ),
60 | 'label' => 'Unit',
61 | 'translation_domain' => 'dashboard'
62 | ))
63 | ->add('save', SubmitType::class, array(
64 | 'label' => 'Add Resource',
65 | 'translation_domain' => 'dashboard'
66 | ));
67 | }
68 | }
--------------------------------------------------------------------------------
/src/AppBundle/Form/SettingType.php:
--------------------------------------------------------------------------------
1 | add('mqttHost', TextType::class, array(
15 | 'attr' => array('maxlength' => 200),
16 | 'label' => 'MQTT Host',
17 | 'translation_domain' => 'dashboard'
18 | ))
19 | ->add('mqttPort', TextType::class, array(
20 | 'attr' => array('maxlength' => 200),
21 | 'label' => 'MQTT Port',
22 | 'translation_domain' => 'dashboard'
23 | ))
24 | ->add('save', SubmitType::class, array(
25 | 'label' => 'Save',
26 | 'translation_domain' => 'dashboard'
27 | ));
28 | }
29 | }
--------------------------------------------------------------------------------
/src/AppBundle/Form/TaskType.php:
--------------------------------------------------------------------------------
1 | add('name', TextType::class, array(
19 | 'label' => 'Name',
20 | 'translation_domain' => 'dashboard'
21 | ))
22 | ->add('notes', TextareaType::class, array(
23 | 'required' => false,
24 | 'label' => 'Note',
25 | 'translation_domain' => 'dashboard'
26 | ))
27 | ->add('category', ChoiceType::class, array(
28 | 'choices' => array(
29 | 'Area' => 'area',
30 | 'Plant' => 'plant',
31 | 'Seed' => 'seed',
32 | 'Reservoir' => 'reservoir',
33 | ),
34 | 'label' => 'Category',
35 | 'translation_domain' => 'dashboard'
36 | ))
37 | ->add('dueDate', DateTimeType::class, array(
38 | 'years' => range(date('Y'), date('Y') + 1),
39 | 'widget' => 'single_text',
40 | 'label' => 'Due date',
41 | 'translation_domain' => 'dashboard'
42 | ))
43 | ->add('urgencyLevel', ChoiceType::class, array(
44 | 'choices' => array(
45 | 'Low' => 'low',
46 | 'Medium' => 'medium',
47 | 'High' => 'high',
48 | ),
49 | 'label' => 'Level of urgency',
50 | 'translation_domain' => 'dashboard'
51 | ))
52 | ->add('isDone', ChoiceType::class, array(
53 | 'choices' => array(
54 | 'No' => 0,
55 | 'Yes' => 1,
56 | ),
57 | 'label' => 'Is it done?',
58 | 'translation_domain' => 'dashboard'
59 | ))
60 | ->add('save', SubmitType::class, array(
61 | 'label' => 'Save',
62 | 'translation_domain' => 'dashboard'
63 | ));
64 | }
65 | }
66 |
--------------------------------------------------------------------------------
/src/AppBundle/Repository/AbstractRepository.php:
--------------------------------------------------------------------------------
1 |
10 | */
11 | abstract class AbstractRepository
12 | {
13 | /**
14 | * @var EntityManager
15 | */
16 | private $manager;
17 |
18 | /**
19 | * @var string
20 | */
21 | private $class;
22 |
23 | /**
24 | * @param EntityManager $entityManager
25 | * @param string $class
26 | */
27 | public function __construct(EntityManager $entityManager, $class)
28 | {
29 | $this->manager = $entityManager;
30 | $this->class = $class;
31 | }
32 |
33 | /**
34 | * @return EntityRepository
35 | */
36 | protected function getRepository()
37 | {
38 | return $this->manager->getRepository($this->class);
39 | }
40 | }
41 |
--------------------------------------------------------------------------------
/src/AppBundle/Repository/TaskRepository.php:
--------------------------------------------------------------------------------
1 |
9 | */
10 | class TaskRepository extends AbstractRepository
11 | {
12 | /**
13 | * @param int $limit
14 | * @param int $farmId
15 | *
16 | * @return Task[]
17 | */
18 | public function deadlineTasks($farmId, $limit = 9)
19 | {
20 | $qb = $this->getRepository()->createQueryBuilder('t');
21 |
22 | $query = $qb
23 | ->select('t')
24 | ->orderBy('t.dueDate', 'ASC')
25 | ->where('t.isDone = 0')
26 | ->andWhere('t.field = '.$farmId)
27 | ->setMaxResults(5)
28 | ->getQuery();
29 |
30 | return $query->getResult();
31 | }
32 |
33 | /**
34 | * @param int $farmId
35 | *
36 | * @return int
37 | */
38 | public function countByFarm($farmId)
39 | {
40 | $qb = $this->getRepository()->createQueryBuilder('t');
41 |
42 | $qb->select($qb->expr()->count('t'))
43 | ->where('t.field = '.$farmId);
44 |
45 | $query = $qb->getQuery();
46 |
47 | return $query->getSingleScalarResult();
48 | }
49 | }
50 |
--------------------------------------------------------------------------------
/tests/AppBundle/Controller/AreaControllerTest.php:
--------------------------------------------------------------------------------
1 | 'testuser',
13 | 'PHP_AUTH_PW' => 'test123'
14 | ));
15 |
16 | $crawler = $client->request('GET', '/areas');
17 |
18 | $this->assertEquals(200, $client->getResponse()->getStatusCode());
19 | }
20 | }
21 |
--------------------------------------------------------------------------------
/tests/AppBundle/Controller/DashboardControllerTest.php:
--------------------------------------------------------------------------------
1 | 'testuser',
14 | 'PHP_AUTH_PW' => 'test123'
15 | ));
16 |
17 | $container = $client->getContainer();
18 | $container->get('session')->set('activeFarm', 1);
19 |
20 | $crawler = $client->request('GET', '/');
21 |
22 | $this->assertEquals(302, $client->getResponse()->getStatusCode());
23 | }
24 | }
25 |
--------------------------------------------------------------------------------
/tests/AppBundle/Controller/DeviceControllerTest.php:
--------------------------------------------------------------------------------
1 | 'testuser',
13 | 'PHP_AUTH_PW' => 'test123'
14 | ));
15 |
16 | $crawler = $client->request('GET', '/devices');
17 |
18 | $this->assertEquals(200, $client->getResponse()->getStatusCode());
19 | }
20 | }
21 |
--------------------------------------------------------------------------------
/tests/AppBundle/Controller/FieldControllerTest.php:
--------------------------------------------------------------------------------
1 | 'testuser',
13 | 'PHP_AUTH_PW' => 'test123'
14 | ));
15 |
16 | $crawler = $client->request('GET', '/farms');
17 |
18 | $this->assertEquals(200, $client->getResponse()->getStatusCode());
19 | }
20 | }
21 |
--------------------------------------------------------------------------------
/tests/AppBundle/Controller/InventoryControllerTest.php:
--------------------------------------------------------------------------------
1 | 'testuser',
13 | 'PHP_AUTH_PW' => 'test123'
14 | ));
15 |
16 | $crawler = $client->request('GET', '/inventories');
17 |
18 | $this->assertEquals(200, $client->getResponse()->getStatusCode());
19 | }
20 | }
21 |
--------------------------------------------------------------------------------
/tests/AppBundle/Controller/PlantControllerTest.php:
--------------------------------------------------------------------------------
1 | 'testuser',
14 | 'PHP_AUTH_PW' => 'test123'
15 | ));
16 |
17 | $container = $client->getContainer();
18 | $container->get('session')->set('activeFarm', 1);
19 |
20 | $crawler = $client->request('GET', '/plants');
21 |
22 | $this->assertEquals(200, $client->getResponse()->getStatusCode());
23 | }
24 | }
25 |
--------------------------------------------------------------------------------
/tests/AppBundle/Controller/ReservoirControllerTest.php:
--------------------------------------------------------------------------------
1 | 'testuser',
13 | 'PHP_AUTH_PW' => 'test123'
14 | ));
15 |
16 | $crawler = $client->request('GET', '/reservoirs');
17 |
18 | $this->assertEquals(200, $client->getResponse()->getStatusCode());
19 | }
20 | }
21 |
--------------------------------------------------------------------------------
/tests/AppBundle/Controller/TaskControllerTest.php:
--------------------------------------------------------------------------------
1 | 'testuser',
13 | 'PHP_AUTH_PW' => 'test123'
14 | ));
15 |
16 | $crawler = $client->request('GET', '/tasks');
17 |
18 | $this->assertEquals(200, $client->getResponse()->getStatusCode());
19 | }
20 | }
21 |
--------------------------------------------------------------------------------
/var/cache/.gitkeep:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/var/cache/.gitkeep
--------------------------------------------------------------------------------
/var/logs/.gitkeep:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/var/logs/.gitkeep
--------------------------------------------------------------------------------
/var/sessions/.gitkeep:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/var/sessions/.gitkeep
--------------------------------------------------------------------------------
/web.config:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 |
24 |
25 |
26 |
27 |
28 |
29 |
30 |
31 |
32 |
33 |
34 |
--------------------------------------------------------------------------------
/web/.htaccess:
--------------------------------------------------------------------------------
1 | # Use the front controller as index file. It serves as a fallback solution when
2 | # every other rewrite/redirect fails (e.g. in an aliased environment without
3 | # mod_rewrite). Additionally, this reduces the matching process for the
4 | # start page (path "/") because otherwise Apache will apply the rewriting rules
5 | # to each configured DirectoryIndex file (e.g. index.php, index.html, index.pl).
6 | DirectoryIndex app.php
7 |
8 | # By default, Apache does not evaluate symbolic links if you did not enable this
9 | # feature in your server configuration. Uncomment the following line if you
10 | # install assets as symlinks or if you experience problems related to symlinks
11 | # when compiling LESS/Sass/CoffeScript assets.
12 | # Options FollowSymlinks
13 |
14 | # Disabling MultiViews prevents unwanted negotiation, e.g. "/app" should not resolve
15 | # to the front controller "/app.php" but be rewritten to "/app.php/app".
16 |
17 | Options -MultiViews
18 |
19 |
20 |
21 | RewriteEngine On
22 |
23 | # Determine the RewriteBase automatically and set it as environment variable.
24 | # If you are using Apache aliases to do mass virtual hosting or installed the
25 | # project in a subdirectory, the base path will be prepended to allow proper
26 | # resolution of the app.php file and to redirect to the correct URI. It will
27 | # work in environments without path prefix as well, providing a safe, one-size
28 | # fits all solution. But as you do not need it in this case, you can comment
29 | # the following 2 lines to eliminate the overhead.
30 | RewriteCond %{REQUEST_URI}::$1 ^(/.+)/(.*)::\2$
31 | RewriteRule ^(.*) - [E=BASE:%1]
32 |
33 | # Sets the HTTP_AUTHORIZATION header removed by Apache
34 | RewriteCond %{HTTP:Authorization} .
35 | RewriteRule ^ - [E=HTTP_AUTHORIZATION:%{HTTP:Authorization}]
36 |
37 | # Redirect to URI without front controller to prevent duplicate content
38 | # (with and without `/app.php`). Only do this redirect on the initial
39 | # rewrite by Apache and not on subsequent cycles. Otherwise we would get an
40 | # endless redirect loop (request -> rewrite to front controller ->
41 | # redirect -> request -> ...).
42 | # So in case you get a "too many redirects" error or you always get redirected
43 | # to the start page because your Apache does not expose the REDIRECT_STATUS
44 | # environment variable, you have 2 choices:
45 | # - disable this feature by commenting the following 2 lines or
46 | # - use Apache >= 2.3.9 and replace all L flags by END flags and remove the
47 | # following RewriteCond (best solution)
48 | RewriteCond %{ENV:REDIRECT_STATUS} ^$
49 | RewriteRule ^app\.php(?:/(.*)|$) %{ENV:BASE}/$1 [R=301,L]
50 |
51 | # If the requested filename exists, simply serve it.
52 | # We only want to let Apache serve files and not directories.
53 | RewriteCond %{REQUEST_FILENAME} -f
54 | RewriteRule ^ - [L]
55 |
56 | # Rewrite all other queries to the front controller.
57 | RewriteRule ^ %{ENV:BASE}/app.php [L]
58 |
59 |
60 |
61 |
62 | # When mod_rewrite is not available, we instruct a temporary redirect of
63 | # the start page to the front controller explicitly so that the website
64 | # and the generated links can still be used.
65 | RedirectMatch 302 ^/$ /app.php/
66 | # RedirectTemp cannot be used instead
67 |
68 |
69 |
--------------------------------------------------------------------------------
/web/app.php:
--------------------------------------------------------------------------------
1 | handle($request);
19 | $response->send();
20 | $kernel->terminate($request, $response);
21 |
--------------------------------------------------------------------------------
/web/apple-touch-icon.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/apple-touch-icon.png
--------------------------------------------------------------------------------
/web/assets/css/.DS_Store:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/css/.DS_Store
--------------------------------------------------------------------------------
/web/assets/css/material-design-icons/fonts/Material-Design-Iconic-Font.eot:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/css/material-design-icons/fonts/Material-Design-Iconic-Font.eot
--------------------------------------------------------------------------------
/web/assets/css/material-design-icons/fonts/Material-Design-Iconic-Font.ttf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/css/material-design-icons/fonts/Material-Design-Iconic-Font.ttf
--------------------------------------------------------------------------------
/web/assets/css/material-design-icons/fonts/Material-Design-Iconic-Font.woff:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/css/material-design-icons/fonts/Material-Design-Iconic-Font.woff
--------------------------------------------------------------------------------
/web/assets/css/material-design-icons/fonts/Material-Design-Iconic-Font.woff2:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/css/material-design-icons/fonts/Material-Design-Iconic-Font.woff2
--------------------------------------------------------------------------------
/web/assets/css/material-design-icons/less/border.less:
--------------------------------------------------------------------------------
1 | // Bordered icons
2 | // -------------------------
3 |
4 | .@{zmdi-css-prefix}-border {
5 | padding: .1em .25em;
6 | border: solid .1em @md-border-color;
7 | border-radius: 2px;
8 | }
9 |
10 | .@{zmdi-css-prefix}-border-circle {
11 | padding: .1em .25em;
12 | border: solid .1em @md-border-color;
13 | border-radius: 50%;
14 | }
15 |
--------------------------------------------------------------------------------
/web/assets/css/material-design-icons/less/core.less:
--------------------------------------------------------------------------------
1 | // Core Class Definition
2 | // -------------------------
3 |
4 | .@{zmdi-icon-prefix} {
5 | display: inline-block;
6 | font: normal normal normal 14px/1 '@{zmdi-font-name}';
7 | font-size: inherit;
8 | text-rendering: auto;
9 | -webkit-font-smoothing: antialiased;
10 | -moz-osx-font-smoothing: grayscale;
11 | }
12 |
--------------------------------------------------------------------------------
/web/assets/css/material-design-icons/less/fixed-width.less:
--------------------------------------------------------------------------------
1 | // Fixed Width Icons
2 | // -------------------------
3 |
4 | .@{zmdi-css-prefix}-fw {
5 | width: (18em / 14);
6 | text-align: center;
7 | }
--------------------------------------------------------------------------------
/web/assets/css/material-design-icons/less/list.less:
--------------------------------------------------------------------------------
1 | // List Icons
2 | // -------------------------
3 |
4 | .@{zmdi-css-prefix}-ul {
5 | padding-left: 0;
6 | margin-left: @zmdi-li-width;
7 | list-style-type: none;
8 | > li {
9 | position: relative;
10 | }
11 | }
12 | .@{zmdi-css-prefix}-li {
13 | position: absolute;
14 | left: -@zmdi-li-width;
15 | width: @zmdi-li-width;
16 | top: (2em / 14);
17 | text-align: center;
18 | &.@{zmdi-css-prefix}-lg {
19 | left: (-@zmdi-li-width + (4em / 14));
20 | }
21 | }
--------------------------------------------------------------------------------
/web/assets/css/material-design-icons/less/material-design-iconic-font.less:
--------------------------------------------------------------------------------
1 | /*!
2 | * Material Design Iconic Font by Sergey Kupletsky (@zavoloklom) - http://zavoloklom.github.io/material-design-iconic-font/
3 | * License - http://zavoloklom.github.io/material-design-iconic-font/license (Font: SIL OFL 1.1, CSS: MIT License)
4 | */
5 |
6 | @import "variables.less";
7 | @import "path.less";
8 | @import "core.less";
9 | @import "sizes.less";
10 | @import "fixed-width.less";
11 | @import "list.less";
12 | @import "border.less";
13 | @import "pulled.less";
14 | @import "spinned.less";
15 | @import "rotated.less";
16 | @import "stacked.less";
17 | @import "icons.less";
18 | @import "aliases.less";
--------------------------------------------------------------------------------
/web/assets/css/material-design-icons/less/path.less:
--------------------------------------------------------------------------------
1 | // Font path
2 | // --------------------------
3 |
4 | @font-face {
5 | font-family: '@{zmdi-font-name}';
6 | src:
7 | url('@{zmdi-font-path}/Material-Design-Iconic-Font.woff2?v=@{zmdi-version}') format('woff2'),
8 | url('@{zmdi-font-path}/Material-Design-Iconic-Font.woff?v=@{zmdi-version}') format('woff'),
9 | url('@{zmdi-font-path}/Material-Design-Iconic-Font.ttf?v=@{zmdi-version}') format('truetype');
10 | font-weight: normal;
11 | font-style: normal;
12 | }
--------------------------------------------------------------------------------
/web/assets/css/material-design-icons/less/pulled.less:
--------------------------------------------------------------------------------
1 | // Pulled icons
2 | // -------------------------
3 |
4 | .@{zmdi-icon-prefix} {
5 | &.pull-left {
6 | float: left;
7 | margin-right: .15em;
8 | }
9 | &.pull-right {
10 | float: right;
11 | margin-left: .15em;
12 | }
13 | }
14 |
--------------------------------------------------------------------------------
/web/assets/css/material-design-icons/less/rotated.less:
--------------------------------------------------------------------------------
1 | // Rotated & Flipped icons
2 | // -------------------------
3 |
4 | .@{zmdi-css-prefix}-rotate-90 {
5 | transform: rotate(90deg);
6 | }
7 | .@{zmdi-css-prefix}-rotate-180 {
8 | transform: rotate(180deg);
9 | }
10 | .@{zmdi-css-prefix}-rotate-270 {
11 | transform: rotate(270deg);
12 | }
13 |
14 | .@{zmdi-css-prefix}-flip-horizontal {
15 | transform: scale(-1, 1);
16 | }
17 | .@{zmdi-css-prefix}-flip-vertical {
18 | transform: scale(1, -1);
19 | }
--------------------------------------------------------------------------------
/web/assets/css/material-design-icons/less/sizes.less:
--------------------------------------------------------------------------------
1 | // Icon sizes
2 | // -------------------------
3 |
4 | .@{zmdi-css-prefix}-lg {
5 | font-size: (4em / 3);
6 | line-height: (3em / 4);
7 | vertical-align: -15%;
8 | }
9 | .@{zmdi-css-prefix}-2x {
10 | font-size: 2em;
11 | }
12 | .@{zmdi-css-prefix}-3x {
13 | font-size: 3em;
14 | }
15 | .@{zmdi-css-prefix}-4x {
16 | font-size: 4em;
17 | }
18 | .@{zmdi-css-prefix}-5x {
19 | font-size: 5em;
20 | }
--------------------------------------------------------------------------------
/web/assets/css/material-design-icons/less/spinned.less:
--------------------------------------------------------------------------------
1 | // Spinning Icons
2 | // --------------------------
3 |
4 | .@{zmdi-css-prefix}-spin {
5 | animation: zmdi-spin 1.5s infinite linear;
6 | }
7 |
8 | .@{zmdi-css-prefix}-spin-reverse {
9 | animation: zmdi-spin-reverse 1.5s infinite linear;
10 | }
11 |
12 | // Spin
13 | @keyframes zmdi-spin {
14 | 0% {
15 | transform: rotate(0deg);
16 | }
17 | 100% {
18 | transform: rotate(359deg);
19 | }
20 | }
21 |
22 | // Spin Reverse
23 | @keyframes zmdi-spin-reverse {
24 | 0% {
25 | transform: rotate(0deg);
26 | }
27 | 100% {
28 | transform: rotate(-359deg);
29 | }
30 | }
31 |
32 |
--------------------------------------------------------------------------------
/web/assets/css/material-design-icons/less/stacked.less:
--------------------------------------------------------------------------------
1 | // Stacked Icons
2 | // -------------------------
3 |
4 | .@{zmdi-css-prefix}-stack {
5 | position: relative;
6 | display: inline-block;
7 | width: 2em;
8 | height: 2em;
9 | line-height: 2em;
10 | vertical-align: middle;
11 | }
12 | .@{zmdi-css-prefix}-stack-1x, .@{zmdi-css-prefix}-stack-2x {
13 | position: absolute;
14 | left: 0;
15 | width: 100%;
16 | text-align: center;
17 | }
18 | .@{zmdi-css-prefix}-stack-1x {
19 | line-height: inherit;
20 | }
21 | .@{zmdi-css-prefix}-stack-2x {
22 | font-size: 2em;
23 | }
24 | .@{zmdi-css-prefix}-inverse {
25 | color: @zmdi-inverse;
26 | }
--------------------------------------------------------------------------------
/web/assets/css/material-design-icons/less/variables.less:
--------------------------------------------------------------------------------
1 | // Variables
2 | // --------------------------
3 |
4 | @zmdi-font-name: "Material Icons";
5 | @zmdi-font-path: "../fonts";
6 | @zmdi-css-prefix: mdi-hc;
7 | @zmdi-icon-prefix: mdi;
8 | @zmdi-version: "2.2.0";
9 |
10 | @zmdi-border-color: #9E9E9E;
11 | @zmdi-inverse: #FFFFFF;
12 | @zmdi-li-width: (30em / 14);
13 |
14 | // Legacy code for backward capability with 2.0.x version
15 |
16 | @md-font-path: "../fonts";
17 | @md-css-prefix: md;
18 | @md-icon-prefix: mdi;
19 | @md-version: "2.2.0";
20 |
21 | @md-border-color: #9E9E9E;
22 | @md-inverse: #FFFFFF;
23 | @md-li-width: (30em / 14);
--------------------------------------------------------------------------------
/web/assets/fonts/glyphicons-halflings-regular.eot:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/fonts/glyphicons-halflings-regular.eot
--------------------------------------------------------------------------------
/web/assets/fonts/glyphicons-halflings-regular.ttf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/fonts/glyphicons-halflings-regular.ttf
--------------------------------------------------------------------------------
/web/assets/fonts/glyphicons-halflings-regular.woff:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/fonts/glyphicons-halflings-regular.woff
--------------------------------------------------------------------------------
/web/assets/fonts/glyphicons-halflings-regular.woff2:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/fonts/glyphicons-halflings-regular.woff2
--------------------------------------------------------------------------------
/web/assets/img/favicon.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/img/favicon.png
--------------------------------------------------------------------------------
/web/assets/img/logo.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/img/logo.png
--------------------------------------------------------------------------------
/web/assets/img/plant-basil.jpg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/img/plant-basil.jpg
--------------------------------------------------------------------------------
/web/assets/img/tania.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/img/tania.png
--------------------------------------------------------------------------------
/web/assets/js/area.js:
--------------------------------------------------------------------------------
1 | (function() {
2 | $(document).ready(function() {
3 | /* form validation here */
4 | $('#area_name').keyup(function(e) {
5 | var maxLength = 50;
6 | var textlen = $(this).val().length;
7 |
8 | if(textlen <= maxLength) {
9 | var spanText = "Name ("+textlen+"/"+maxLength+" chars)";
10 | $('#label_area_name').text(spanText);
11 | }
12 | });
13 | });
14 | })();
--------------------------------------------------------------------------------
/web/assets/js/dashboard.js:
--------------------------------------------------------------------------------
1 | (function() {
2 | $(document).ready(function() {
3 | var fieldMap = L.map('map');
4 | var locations = $('#map').data('locations');
5 | var markers = [];
6 |
7 | L.tileLayer('https://api.tiles.mapbox.com/v4/{id}/{z}/{x}/{y}.png?access_token=pk.eyJ1IjoibWFwYm94IiwiYSI6ImNpejY4NXVycTA2emYycXBndHRqcmZ3N3gifQ.rJcFIG214AriISLbB6B5aw', {
8 | maxZoom: 18,
9 | attribution: 'Map data © OpenStreetMap contributors, ' +
10 | 'CC-BY-SA , ' +
11 | 'Imagery © Mapbox ',
12 | id: 'mapbox.streets'
13 | }).addTo(fieldMap);
14 |
15 | locations.forEach(function(latLng) {
16 | if(latLng[0] !== null || latLng[1] !== null) {
17 | // create the marker
18 | var marker = L.marker(latLng);
19 | markers.push(marker);
20 | }
21 | });
22 |
23 | var group = new L.featureGroup(markers);
24 | fieldMap.fitBounds(group.getBounds());
25 | group.addTo(fieldMap);
26 | });
27 | })();
--------------------------------------------------------------------------------
/web/assets/js/field-map-show.js:
--------------------------------------------------------------------------------
1 | (function() {
2 | $(document).ready(function() {
3 | var fieldMap, markerLayer;
4 | var currentLatLng = [$('#map').data('lat'), $('#map').data('lng')];
5 | var defaultLatLng = [-8.4960936, 115.2485298];
6 |
7 | /* Initialize the map and tile layer */
8 | function mapInit(latLng) {
9 | fieldMap = L.map('map').setView(latLng, 13);
10 | markerLayer = L.marker(latLng).addTo(fieldMap);
11 |
12 | L.tileLayer('https://api.tiles.mapbox.com/v4/{id}/{z}/{x}/{y}.png?access_token=pk.eyJ1IjoibWFwYm94IiwiYSI6ImNpejY4NXVycTA2emYycXBndHRqcmZ3N3gifQ.rJcFIG214AriISLbB6B5aw', {
13 | maxZoom: 18,
14 | attribution: 'Map data © OpenStreetMap contributors, ' +
15 | 'CC-BY-SA , ' +
16 | 'Imagery © Mapbox ',
17 | id: 'mapbox.streets'
18 | }).addTo(fieldMap);
19 | }
20 |
21 | /* Get current lat and lng from the click on top of map */
22 | function onMapClick(e) {
23 | fieldMap.removeLayer(markerLayer);
24 |
25 | $('#field_lat').val(e.latlng.lat);
26 | $('#field_lng').val(e.latlng.lng);
27 |
28 | markerLayer = L.marker([e.latlng.lat, e.latlng.lng]).addTo(fieldMap);
29 | }
30 |
31 | if(currentLatLng[0] === "" || currentLatLng[1] === "") {
32 | if("geolocation" in navigator){
33 | navigator.geolocation.getCurrentPosition(function(position){
34 | mapInit([position.coords.latitude, position.coords.longitude]);
35 | fieldMap.on('click', onMapClick);
36 | }, function(error) {
37 | // if error it will use default lat lng
38 | mapInit(defaultLatLng);
39 | fieldMap.on('click', onMapClick);
40 | });
41 | } else {
42 | mapInit(defaultLatLng);
43 | fieldMap.on('click', onMapClick);
44 | }
45 | } else {
46 | mapInit(currentLatLng);
47 | fieldMap.on('click', onMapClick);
48 | }
49 |
50 | /* form validation here */
51 | $('#field_name').keyup(function(e) {
52 | var maxLength = 50;
53 | var textlen = $(this).val().length;
54 |
55 | if(textlen <= maxLength) {
56 | var spanText = "Name ("+textlen+"/"+maxLength+" chars)";
57 | $('#label_field_name').text(spanText);
58 | }
59 | });
60 | });
61 | })();
--------------------------------------------------------------------------------
/web/assets/js/field-map.js:
--------------------------------------------------------------------------------
1 | (function() {
2 | $(document).ready(function() {
3 | var fieldMap, markerLayer;
4 | var defaultLatLng = [-8.4960936, 115.2485298];
5 |
6 | /* Initialize the map and tile layer */
7 | function mapInit(latLng) {
8 | fieldMap = L.map('map').setView(latLng, 13);
9 | markerLayer = L.marker(latLng).addTo(fieldMap);
10 |
11 | L.tileLayer('https://api.tiles.mapbox.com/v4/{id}/{z}/{x}/{y}.png?access_token=pk.eyJ1IjoibWFwYm94IiwiYSI6ImNpejY4NXVycTA2emYycXBndHRqcmZ3N3gifQ.rJcFIG214AriISLbB6B5aw', {
12 | maxZoom: 18,
13 | attribution: 'Map data © OpenStreetMap contributors, ' +
14 | 'CC-BY-SA , ' +
15 | 'Imagery © Mapbox ',
16 | id: 'mapbox.streets'
17 | }).addTo(fieldMap);
18 | }
19 |
20 | /* Get current lat and lng from the click on top of map */
21 | function onMapClick(e) {
22 | fieldMap.removeLayer(markerLayer);
23 |
24 | $('#field_lat').val(e.latlng.lat);
25 | $('#field_lng').val(e.latlng.lng);
26 |
27 | markerLayer = L.marker([e.latlng.lat, e.latlng.lng]).addTo(fieldMap);
28 | }
29 |
30 | if("geolocation" in navigator){
31 | navigator.geolocation.getCurrentPosition(function(position){
32 | mapInit([position.coords.latitude, position.coords.longitude]);
33 | fieldMap.on('click', onMapClick);
34 |
35 | // Automatically fill the lat lng input fields
36 | $('#field_lat').val(position.coords.latitude);
37 | $('#field_lng').val(position.coords.longitude);
38 | }, function(error) {
39 | // if error it will use default lat lng
40 | mapInit(defaultLatLng);
41 | fieldMap.on('click', onMapClick);
42 |
43 | // Automatically fill the lat lng input fields
44 | $('#field_lat').val(position.coords.latitude);
45 | $('#field_lng').val(position.coords.longitude);
46 | });
47 | } else {
48 | mapInit(defaultLatLng);
49 | fieldMap.on('click', onMapClick);
50 |
51 | // Automatically fill the lat lng input fields
52 | $('#field_lat').val(position.coords.latitude);
53 | $('#field_lng').val(position.coords.longitude);
54 | }
55 |
56 | /* form validation here */
57 | $('#field_name').keyup(function(e) {
58 | var maxLength = 50;
59 | var textlen = $(this).val().length;
60 |
61 | if(textlen <= maxLength) {
62 | var spanText = "Name ("+textlen+"/"+maxLength+" chars)";
63 | $('#label_field_name').text(spanText);
64 | }
65 | });
66 | });
67 | })();
--------------------------------------------------------------------------------
/web/assets/js/npm.js:
--------------------------------------------------------------------------------
1 | // This file is autogenerated via the `commonjs` Grunt task. You can require() this file in a CommonJS environment.
2 | require('../../js/transition.js')
3 | require('../../js/alert.js')
4 | require('../../js/button.js')
5 | require('../../js/carousel.js')
6 | require('../../js/collapse.js')
7 | require('../../js/dropdown.js')
8 | require('../../js/modal.js')
9 | require('../../js/tooltip.js')
10 | require('../../js/popover.js')
11 | require('../../js/scrollspy.js')
12 | require('../../js/tab.js')
13 | require('../../js/affix.js')
--------------------------------------------------------------------------------
/web/assets/js/plant.js:
--------------------------------------------------------------------------------
1 | jQuery.datetimepicker.setLocale(global.locale);
2 | $(".date-picker").datetimepicker({
3 | format: 'Y-m-d',
4 | timepicker: false
5 | });
--------------------------------------------------------------------------------
/web/assets/js/task.js:
--------------------------------------------------------------------------------
1 | jQuery.datetimepicker.setLocale(global.locale);
2 | $(".date-time-picker").datetimepicker({
3 | format: 'Y-m-d H:i'
4 | });
5 |
--------------------------------------------------------------------------------
/web/assets/lib/.DS_Store:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/.DS_Store
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-Black.eot:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-Black.eot
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-Black.ttf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-Black.ttf
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-Black.woff:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-Black.woff
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-Black.woff2:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-Black.woff2
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-BlackItalic.eot:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-BlackItalic.eot
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-BlackItalic.ttf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-BlackItalic.ttf
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-BlackItalic.woff:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-BlackItalic.woff
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-BlackItalic.woff2:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-BlackItalic.woff2
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-Bold.eot:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-Bold.eot
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-Bold.ttf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-Bold.ttf
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-Bold.woff:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-Bold.woff
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-Bold.woff2:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-Bold.woff2
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-BoldItalic.eot:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-BoldItalic.eot
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-BoldItalic.ttf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-BoldItalic.ttf
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-BoldItalic.woff:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-BoldItalic.woff
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-BoldItalic.woff2:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-BoldItalic.woff2
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-Light.eot:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-Light.eot
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-Light.ttf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-Light.ttf
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-Light.woff:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-Light.woff
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-Light.woff2:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-Light.woff2
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-LightItalic.eot:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-LightItalic.eot
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-LightItalic.ttf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-LightItalic.ttf
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-LightItalic.woff:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-LightItalic.woff
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-LightItalic.woff2:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-LightItalic.woff2
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-Medium.eot:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-Medium.eot
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-Medium.ttf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-Medium.ttf
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-Medium.woff:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-Medium.woff
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-Medium.woff2:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-Medium.woff2
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-MediumItalic.eot:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-MediumItalic.eot
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-MediumItalic.ttf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-MediumItalic.ttf
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-MediumItalic.woff:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-MediumItalic.woff
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-MediumItalic.woff2:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-MediumItalic.woff2
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-Regular.eot:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-Regular.eot
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-Regular.ttf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-Regular.ttf
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-Regular.woff:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-Regular.woff
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-Regular.woff2:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-Regular.woff2
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-RegularItalic.eot:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-RegularItalic.eot
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-RegularItalic.ttf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-RegularItalic.ttf
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-RegularItalic.woff:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-RegularItalic.woff
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-RegularItalic.woff2:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-RegularItalic.woff2
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-Thin.eot:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-Thin.eot
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-Thin.ttf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-Thin.ttf
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-Thin.woff:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-Thin.woff
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-Thin.woff2:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-Thin.woff2
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-ThinItalic.eot:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-ThinItalic.eot
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-ThinItalic.ttf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-ThinItalic.ttf
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-ThinItalic.woff:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-ThinItalic.woff
--------------------------------------------------------------------------------
/web/assets/lib/roboto/Roboto-ThinItalic.woff2:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/assets/lib/roboto/Roboto-ThinItalic.woff2
--------------------------------------------------------------------------------
/web/debug.html:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/debug.html
--------------------------------------------------------------------------------
/web/favicon.ico:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/favicon.ico
--------------------------------------------------------------------------------
/web/robots.txt:
--------------------------------------------------------------------------------
1 | # www.robotstxt.org/
2 | # www.google.com/support/webmasters/bin/answer.py?hl=en&answer=156449
3 |
4 | User-agent: *
5 | Disallow:
6 |
--------------------------------------------------------------------------------
/web/uploads/areas/index.html:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/uploads/areas/index.html
--------------------------------------------------------------------------------
/web/uploads/fields/index.html:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/uploads/fields/index.html
--------------------------------------------------------------------------------
/web/uploads/seeds/index.html:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/usetania/tania/c682c132cbec91da56df9ff0958060f504ee6381/web/uploads/seeds/index.html
--------------------------------------------------------------------------------