diff --git a/CHANGELOG.md b/CHANGELOG.md index 9565b7c3410a9a65280623a83095150c844cde2f..97fb7ab03ec45122ed9f65e3b562488ae4b33d38 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,6 +4,16 @@ All notable changes to this project will be documented in this file. The format is based on [Keep a Changelog](http://keepachangelog.com/) and this project adheres to [Semantic Versioning](http://semver.org/). +## 1.8.0 - 2018-11-13 +### Added +- Add financial route +- Add employees route +### Changed +- Fix school route +- Fix transport route +- Fix return where integral time is null +- Classroom count route returns school year results for education level 1 + ## 1.7.0 - 2018-09-20 ### Changed - Fix return string in contract type id 1 diff --git a/src/libs/convert/integralTime.js b/src/libs/convert/integralTime.js new file mode 100644 index 0000000000000000000000000000000000000000..48f69c43af8b570e131c70ed5a795727530b2e29 --- /dev/null +++ b/src/libs/convert/integralTime.js @@ -0,0 +1,8 @@ +module.exports = function integralTime(id) { + if (id == null) + return 'Não se aplica (semi presencial e EaD)'; + else if (id == false) + return 'Não'; + else if (id == true) + return 'Sim'; +}; diff --git a/src/libs/convert/period.js b/src/libs/convert/period.js index 06dbcf588e58ea2739b2e556ceac8a23ba8939d5..600a71dfde47d9a09421434fe5b9a29599063a53 100644 --- a/src/libs/convert/period.js +++ b/src/libs/convert/period.js @@ -7,6 +7,6 @@ module.exports = function period(id) { case 3: return 'Noturno'; default: - return 'Indefinido'; + return 'Não se aplica (semi presencial e EaD)'; } }; diff --git a/src/libs/middlewares/id2str.js b/src/libs/middlewares/id2str.js index 0a0c2af993a392d86b185e234c2eae448992d1b9..30bf81229a8933029900ada49c50df2ab6e5c7a6 100644 --- a/src/libs/middlewares/id2str.js +++ b/src/libs/middlewares/id2str.js @@ -30,6 +30,8 @@ const useTransport = require(`${libs}/convert/booleanVariable`); const useTransportPublic = require(`${libs}/convert/booleanVariable`); const transportationManager = require(`${libs}/convert/transportationManager`); const specialClass = require(`${libs}/convert/booleanVariable`); +const integralTime = require(`${libs}/convert/integralTime`); +const educationLevelSchoolYear = require(`${libs}/convert/educationLevelSchoolYear`); const ids = { gender_id: gender, @@ -46,7 +48,7 @@ const ids = { location_detailed_id: ruralLocation, ethnic_group_id: ethnicGroup, agreement_id: agreement, - integral_time_id: booleanVariable, + integral_time_id: integralTime, government_agreement_id: booleanVariable, education_day_care_child_id: booleanVariable, education_preschool_child_id: booleanVariable, @@ -71,7 +73,8 @@ const ids = { use_transport_id: useTransport, use_transport_public_id: useTransportPublic, transportation_manager_id: transportationManager, - special_class_id: specialClass + special_class_id: specialClass, + education_level_school_year_id: educationLevelSchoolYear, }; function transform(removeId=false) { @@ -141,5 +144,6 @@ module.exports = { extremesHouseholdIncome, useTransport, transportationManager, - specialClass + specialClass, + integralTime }; diff --git a/src/libs/routes/api.js b/src/libs/routes/api.js index 165f947ec7cedacd66008383042bcca6552712bc..dcd938f36f878c0a855cb61498779e50a6582bbb 100644 --- a/src/libs/routes/api.js +++ b/src/libs/routes/api.js @@ -80,6 +80,9 @@ const classCount = require(`${libs}/routes/classCount`); const portalMecInep = require(`${libs}/routes/portalMecInep`); +const employees = require(`${libs}/routes/employees`); + +const financial = require(`${libs}/routes/financial`); api.get('/', (req, res) => { res.json({ msg: 'SimCAQ API is running' }); @@ -123,5 +126,8 @@ api.use('/auxiliar', auxiliar); api.use('/verify_teacher', verifyTeacher); api.use('/class_count', classCount); api.use('/portal_mec_inep', portalMecInep); +api.use('/employees', employees); +api.use('/financial', financial); + module.exports = api; diff --git a/src/libs/routes/classroomCount.js b/src/libs/routes/classroomCount.js index bdec29e54dca56e3f0eb71184e89645002edf0de..d28de14a3671b6cc0823491f853b2a403fe89030 100644 --- a/src/libs/routes/classroomCount.js +++ b/src/libs/routes/classroomCount.js @@ -163,8 +163,6 @@ classroomCountApp.post('/', rqf.parse(), (req, res, next) => { let classSize = JSON.parse(req.body.class_size) || null; let integralTime = JSON.parse(req.body.integral_time) || null; - console.log(classSize, integralTime); - if(classSize == null || integralTime == null) { res.statusCode = 400; return res.json({err: {message: "There was an error processing class_size or integral_time. Check your JSON sintax and be sure you're sending both paramenters."}}); @@ -197,7 +195,7 @@ classroomCountApp.post('/', rqf.parse(), (req, res, next) => { if(id2str.schoolYear(i) !== id2str.schoolYear(99)) { let educationLevelId = Math.floor(i/10); - let classSize = req.classSize.find((el) => {return el.id === educationLevelId}); + let classSize = req.classSize.find((el) => {return el.id === educationLevelId || el.id === i}); let integralTime = req.integralTime.find((el) => {return el.id === educationLevelId}); let numberStudentClass = (typeof classSize !== 'undefined') ? classSize.numberStudentClass : null; @@ -286,6 +284,7 @@ classroomCountApp.post('/', rqf.parse(), (req, res, next) => { let enrollmentMatch = true; j = 0; let educationLevelSet = new Set(); + let schoolYearSet = new Set(); let enrollment = enrollments[j]; while(enrollmentMatch && j < enrollments.length) { @@ -346,7 +345,11 @@ classroomCountApp.post('/', rqf.parse(), (req, res, next) => { total_classrooms_needed: 0 } }; - + + if(enrollmentEducationLevel.id == 1) { + educationLevel.classes_school_year = []; + } + // Para manter a ordem da etapa de ensino if (location.education_level.length == 0) { location.education_level.push(educationLevel); @@ -375,20 +378,54 @@ classroomCountApp.post('/', rqf.parse(), (req, res, next) => { educationLevel = location.education_level[k]; } + // Adiciona as séries da creche + let currentSchoolYear = null; + if(enrollmentEducationLevel.id == 1){ + let schoolYearHash = '' + enrollment.year + enrollment.city_id + enrollment.location_id + enrollment.school_year_id; + if(schoolYearSet.has(schoolYearHash)) { // Busca a série escolar + let k = 0; + let el = educationLevel.classes_school_year[k]; + while(k < educationLevel.classes_school_year.length) { + if(el.school_year_id != enrollment.school_year_id) { + ++k; + if(k < educationLevel.classes_school_year.length) el = educationLevel.classes_school_year[k]; + } else break; + } + if(k >= educationLevel.classes_school_year.length) --k; + currentSchoolYear = educationLevel.classes_school_year[k]; + } else { // Adiciona uma nova série escolar + let school_year = { + school_year_id: enrollment.school_year_id, + school_year_name: enrollment.school_year_name, + total_enrollment_day: 0, + total_enrollment_night: 0, + full_period_classes: 0, + day_classes: 0, + night_classes: 0, + total_classrooms_needed: 0 + } + schoolYearSet.add(schoolYearHash); + educationLevel.classes_school_year.push(school_year); + currentSchoolYear = school_year; + } + } + + let currentOfferGoal = enrollmentEducationLevel.offerGoal; + let currentNumberStudentClass = (enrollment.location_id == 1) ? enrollmentEducationLevel.numberStudentClass.urban : enrollmentEducationLevel.numberStudentClass.country; + // Soma os totais de matrÃcula da etapa de ensino educationLevel.enrollment.total_enrollment_day += (enrollment.period_id < 3 && enrollment.period_id != null) ? enrollment.total : 0; educationLevel.enrollment.total_enrollment_night += (enrollment.period_id == 3) ? enrollment.total : 0; // Calcula o número de turmas parcial // Turmas de perÃodo integral - educationLevel.enrollment.full_period_classes = Math.ceil((educationLevel.enrollment.total_enrollment_day * (enrollmentEducationLevel.offerGoal/100)) / enrollmentEducationLevel.numberStudentClass); + educationLevel.enrollment.full_period_classes = Math.ceil((educationLevel.enrollment.total_enrollment_day * (currentOfferGoal/100)) / currentNumberStudentClass); - // Turmas diurnas - // MatrÃculas diurnas - matrÃculas integrais - educationLevel.enrollment.day_classes = Math.ceil((educationLevel.enrollment.total_enrollment_day * (1 - enrollmentEducationLevel.offerGoal/100)) / enrollmentEducationLevel.numberStudentClass); + // Turmas diurnas (matrÃculas diurnas - matrÃculas integrais) + educationLevel.enrollment.day_classes = Math.ceil((educationLevel.enrollment.total_enrollment_day * (1 - currentOfferGoal/100)) / currentNumberStudentClass); // Turmas noturnas - educationLevel.enrollment.night_classes = Math.ceil((educationLevel.enrollment.total_enrollment_night / enrollmentEducationLevel.numberStudentClass)); + educationLevel.enrollment.night_classes = Math.ceil((educationLevel.enrollment.total_enrollment_night / currentNumberStudentClass)) || 0; // Total de salas educationLevel.enrollment.total_classrooms_needed = (educationLevel.enrollment.full_period_classes + educationLevel.enrollment.day_classes/2); @@ -397,6 +434,33 @@ classroomCountApp.post('/', rqf.parse(), (req, res, next) => { educationLevel.enrollment.total_classrooms_needed = Math.ceil(educationLevel.enrollment.total_classrooms_needed); + // Faz os mesmos cálculos para a série escolar + if(currentSchoolYear) { + // Totais de matrÃcula + currentSchoolYear.total_enrollment_day += (enrollment.period_id < 3 && enrollment.period_id != null) ? enrollment.total : 0; + currentSchoolYear.total_enrollment_night += (enrollment.period_id == 3) ? enrollment.total : 0; + + // Número de turmas parcial + currentSchoolYear.full_period_classes = Math.ceil((currentSchoolYear.total_enrollment_day * (currentOfferGoal/100)) / currentNumberStudentClass); + + currentSchoolYear.day_classes = Math.ceil((currentSchoolYear.total_enrollment_day * (1 - currentOfferGoal/100)) / currentNumberStudentClass); + + currentSchoolYear.night_classes = Math.ceil((currentSchoolYear.total_enrollment_night / enrollmentEducationLevel.numberStudentClass)) || 0; + + // Total de salas + currentSchoolYear.total_classrooms_needed = (currentSchoolYear.full_period_classes + currentSchoolYear.day_classes/2); + + if(currentSchoolYear.night_classes > (currentSchoolYear.day_classes/2)) currentSchoolYear.total_classrooms_needed += (currentSchoolYear.night_classes - (currentSchoolYear.day_classes/2)); + + currentSchoolYear.total_classrooms_needed = Math.ceil(currentSchoolYear.total_classrooms_needed); + + function reducer(key) { return (sum, elem) => sum + elem[key]} + educationLevel.enrollment.full_period_classes = educationLevel.classes_school_year.reduce(reducer('full_period_classes'), 0); + educationLevel.enrollment.day_classes = educationLevel.classes_school_year.reduce(reducer('day_classes'), 0); + educationLevel.enrollment.night_classes = educationLevel.classes_school_year.reduce(reducer('night_classes'), 0); + educationLevel.enrollment.total_classrooms_needed = educationLevel.classes_school_year.reduce(reducer('total_classrooms_needed'), 0); + } + enrollment = enrollments[j]; } @@ -470,10 +534,11 @@ classroomCountApp.post('/', rqf.parse(), (req, res, next) => { continue; } - // Fazer "merge" do array education_level + // Faz "merge" do array education_level + // Se a localidade atual não tem o vetor if(currentLocation.education_level.length == 0) { currentLocation.education_level = [...cityLocation.education_level]; - } else { + } else { // Caso já tenha, atualiza os valores let l = 0; while(l < cityLocation.education_level.length) { let cityEducation = cityLocation.education_level[l]; @@ -493,6 +558,42 @@ classroomCountApp.post('/', rqf.parse(), (req, res, next) => { currentEducation.enrollment.day_classes += cityEducation.enrollment.day_classes; currentEducation.enrollment.night_classes += cityEducation.enrollment.night_classes; currentEducation.enrollment.total_classrooms_needed += cityEducation.enrollment.total_classrooms_needed; + if((typeof cityEducation.classes_school_year !== 'undefined') && (typeof currentEducation.classes_school_year !== 'undefined')) { + let n = 0; + let o = 0; + let cityClass = null; + let currentClass = null; + while((typeof cityClass !== 'undefined') && (typeof currentClass !== 'undefined')) { + cityClass = cityEducation.classes_school_year[o]; + currentClass = currentEducation.classes_school_year[n]; + + // Se a série escolar é menor que a atual, ela não está no vetor, pois o vetor está ordenado e tem range limitado + if(cityClass.school_year_id < currentClass.school_year_id) { + currentEducation.classes_school_year.splice(n, 0, cityClass); + cityClass = cityEducation.classes_school_year[++o]; + continue; + } else if(cityClass.school_year_id > currentClass.school_year_id) { + currentClass = currentEducation.classes_school_year[++n]; + // Se o ano escolar da cidade é maior que a localidade do objeto atual E o vetor de ano escolar do objeto atual + // acaba, então este ano escolar falta no objeto atual, pois os anos escolares estão ordenados + if(typeof currentClass == 'undefined' && typeof cityClass !== 'undefined') { + currentEducation.classes_school_year[n] = cityClass; + currentClass = currentEducation.classes_school_year[n]; + } + continue; + } + + currentClass.total_enrollment_day += cityClass.total_enrollment_day; + currentClass.total_enrollment_night += cityClass.total_enrollment_night; + currentClass.full_period_classes += cityClass.full_period_classes; + currentClass.day_classes += cityClass.day_classes; + currentClass.night_classes += cityClass.night_classes; + currentClass.total_classrooms_needed += cityClass.total_classrooms_needed; + + cityClass = cityEducation.classes_school_year[++o]; + } + + } } else { if(currentEducation.education_level_short_id < cityEducation.education_level_short_id) { currentLocation.education_level.splice(++m, 0, cityEducation); diff --git a/src/libs/routes/employees.js b/src/libs/routes/employees.js new file mode 100644 index 0000000000000000000000000000000000000000..523eb6bc3cca09977153c7f75d6c31d24e671179 --- /dev/null +++ b/src/libs/routes/employees.js @@ -0,0 +1,517 @@ +const express = require('express'); + +const employeesApp = express.Router(); + +const libs = `${process.cwd()}/libs`; + +const log = require(`${libs}/log`)(module); + +const squel = require('squel'); + +const query = require(`${libs}/middlewares/query`).query; + +const response = require(`${libs}/middlewares/response`); + +const ReqQueryFields = require(`${libs}/middlewares/reqQueryFields`); + +const id2str = require(`${libs}/middlewares/id2str`); + +const config = require(`${libs}/config`); + +const passport = require('passport'); + +const addMissing = require(`${libs}/middlewares/addMissing`); + +const cache = require('apicache').options({ debug: config.debug, statusCodes: {include: [200]} }).middleware; + +let rqfTeacher = new ReqQueryFields(); + +let rqfSchool = new ReqQueryFields(); + + +employeesApp.use(cache('15 day')); + +// Returns a tuple of start and ending years of the complete enrollments dataset. +employeesApp.get('/year_range', (req, res, next) => { + req.sql.from('docente') + .field('MIN(docente.ano_censo)', 'start_year') + .field('MAX(docente.ano_censo)', 'end_year'); + next(); +}, query, response('range')); + +employeesApp.get('/years', (req, res, next) => { + req.sql.from('docente'). + field('DISTINCT docente.ano_censo', 'year'); + next(); +}, query, response('years')); + +employeesApp.get('/source', (req, res, next) => { + req.sql.from('fonte') + .field('fonte', 'source') + .where('tabela = \'docente\''); + next(); +}, query, response('source')); + +employeesApp.get('/adm_dependency_detailed', (req, res, next) => { + req.result = []; + for(let i = 1; i <= 6; ++i) { + req.result.push({ + id: i, + name: id2str.admDependencyPriv(i) + }); + }; + next(); +}, response('adm_dependency_detailed')); + +employeesApp.get('/adm_dependency', (req, res, next) => { + req.result = []; + for(let i = 1; i <= 4; ++i) { + req.result.push({ + id: i, + name: id2str.admDependency(i) + }); + }; + next(); +}, response('adm_dependency')); + +employeesApp.get('/location', (req, res, next) => { + req.result = []; + for(let i = 1; i <= 2; ++i) { + req.result.push({ + id: i, + name: id2str.location(i) + }); + }; + next(); +}, response('location')); + +employeesApp.get('/rural_location', (req, res, next) => { + req.result = [ + {id: 1, name: "Urbana"}, + {id: 2, name: "Rural"}, + {id: 3, name: "Rural - Ãrea de assentamento"}, + {id: 4, name: "Rural - Terra indÃgena"}, + {id: 5, name: "Rural - Ãrea remanescente de quilombos"}, + {id: 6, name: "Rural - Unidade de uso sustentável"} + ]; + next(); +}, response('rural_location')); + +rqfSchool.addField({ + name: 'filter', + field: false, + where: true +}).addField({ + name: 'dims', + field: true, + where: false +}).addValue({ + name: 'adm_dependency', + table: '@', + tableField: 'dependencia_adm_id', + resultField: 'adm_dependency_id', + where: { + relation: '=', + type: 'integer', + field: 'dependencia_adm_id' + } +}).addValue({ + name: 'adm_dependency_detailed', + table: '@', + tableField: 'dependencia_adm_priv', + resultField: 'adm_dependency_detailed_id', + where: { + relation: '=', + type: 'integer', + field: 'dependencia_adm_priv' + } +}).addValue({ + name: 'region', + table: 'regiao', + tableField: 'nome', + resultField: 'region_name', + where: { + relation: '=', + type: 'integer', + field: 'id' + }, + join: { + primary: 'id', + foreign: 'regiao_id', + foreignTable: '@' + } +}).addValue({ + name: 'state', + table: 'estado', + tableField: 'nome', + resultField: 'state_name', + where: { + relation: '=', + type: 'integer', + field: 'id' + }, + join: { + primary: 'id', + foreign: 'estado_id', + foreignTable: '@' + } +}).addValueToField({ + name: 'city', + table: 'municipio', + tableField: ['nome', 'id'], + resultField: ['city_name', 'city_id'], + where: { + relation: '=', + type: 'integer', + field: 'id' + }, + join: { + primary: 'id', + foreign: 'municipio_id', + foreignTable: '@' + } +}, 'dims').addValueToField({ + name: 'city', + table: 'municipio', + tableField: 'nome', + resultField: 'city_name', + where: { + relation: '=', + type: 'integer', + field: 'id' + }, + join: { + primary: 'id', + foreign: 'municipio_id', + foreignTable: '@' + } +}, 'filter').addValueToField({ + name: 'school', + table: 'escola', + tableField: ['nome_escola', 'id'], + resultField: ['school_name', 'school_id'], + where: { + relation: '=', + type: 'integer', + field: 'id' + }, +}, 'dims').addValueToField({ + name: 'school', + table: 'escola', + tableField: 'nome_escola', + resultField: 'school_name', + where: { + relation: '=', + type: 'integer', + field: 'id' + }, +}, 'filter').addValue({ + name: 'location', + table: '@', + tableField: 'cod_localizacao', + resultField: 'location_id', + where: { + relation: '=', + type: 'integer', + field: 'cod_localizacao' + } +}).addValue({ + name: 'rural_location', + table: '@', + tableField: 'localidade_area_rural', + resultField: 'rural_location_id', + where: { + relation: '=', + type: 'integer', + field: 'localidade_area_rural' + } +}).addValue({ + name: 'min_year', + table: '@', + tableField: 'ano_censo', + resultField: 'year', + where: { + relation: '>=', + type: 'integer', + field: 'ano_censo' + } +}).addValue({ + name: 'max_year', + table: '@', + tableField: 'ano_censo', + resultField: 'year', + where: { + relation: '<=', + type: 'integer', + field: 'ano_censo' + } +}); + +rqfTeacher.addField({ + name: 'filter', + field: false, + where: true +}).addField({ + name: 'dims', + field: true, + where: false +}).addValue({ + name: 'adm_dependency', + table: '@', + tableField: 'dependencia_adm_id', + resultField: 'adm_dependency_id', + where: { + relation: '=', + type: 'integer', + field: 'dependencia_adm_id' + } +}).addValue({ + name: 'adm_dependency_detailed', + table: '@', + tableField: 'dependencia_adm_priv', + resultField: 'adm_dependency_detailed_id', + where: { + relation: '=', + type: 'integer', + field: 'dependencia_adm_priv' + } +}).addValue({ + name: 'region', + table: 'regiao', + tableField: 'nome', + resultField: 'region_name', + where: { + relation: '=', + type: 'integer', + field: 'id' + }, + join: { + primary: 'id', + foreign: 'regiao_id', + foreignTable: '@' + } +}).addValue({ + name: 'state', + table: 'estado', + tableField: 'nome', + resultField: 'state_name', + where: { + relation: '=', + type: 'integer', + field: 'id' + }, + join: { + primary: 'id', + foreign: 'estado_id', + foreignTable: '@' + } +}).addValueToField({ + name: 'city', + table: 'municipio', + tableField: ['nome', 'id'], + resultField: ['city_name', 'city_id'], + where: { + relation: '=', + type: 'integer', + field: 'id' + }, + join: { + primary: 'id', + foreign: 'municipio_id', + foreignTable: '@' + } +}, 'dims').addValueToField({ + name: 'city', + table: 'municipio', + tableField: 'nome', + resultField: 'city_name', + where: { + relation: '=', + type: 'integer', + field: 'id' + }, + join: { + primary: 'id', + foreign: 'municipio_id', + foreignTable: '@' + } +}, 'filter').addValueToField({ + name: 'school', + table: 'escola', + tableField: ['nome_escola', 'id'], + resultField: ['school_name', 'school_id'], + where: { + relation: '=', + type: 'integer', + field: 'id' + }, + join: { + primary: ['id','ano_censo'], + foreign: ['escola_id','ano_censo'], + foreignTable: '@' + } +}, 'dims').addValueToField({ + name: 'school', + table: 'escola', + tableField: 'nome_escola', + resultField: 'school_name', + where: { + relation: '=', + type: 'integer', + field: 'id' + }, + join: { + primary: ['id','ano_censo'], + foreign: ['escola_id','ano_censo'], + foreignTable: '@' + } +}, 'filter').addValue({ + name: 'location', + table: '@', + tableField: 'cod_localizacao', + resultField: 'location_id', + where: { + relation: '=', + type: 'integer', + field: 'cod_localizacao' + } +}).addValue({ + name: 'rural_location', + table: '@', + tableField: 'localidade_area_rural', + resultField: 'rural_location_id', + where: { + relation: '=', + type: 'integer', + field: 'localidade_area_rural' + } +}).addValue({ + name: 'min_year', + table: '@', + tableField: 'ano_censo', + resultField: 'year', + where: { + relation: '>=', + type: 'integer', + field: 'ano_censo' + } +}).addValue({ + name: 'max_year', + table: '@', + tableField: 'ano_censo', + resultField: 'year', + where: { + relation: '<=', + type: 'integer', + field: 'ano_censo' + } +}); + + +function matchQueries(queryTotal, queryPartial) { + let match = []; + queryTotal.forEach((result) => { + let newObj = {}; + let keys = Object.keys(result); + keys.forEach((key) => { + newObj[key] = result[key]; + }); + let index = keys.indexOf('total'); + if(index > -1) keys.splice(index, 1); + let objMatch = null; + + for(let i = 0; i < queryPartial.length; ++i) { + let partial = queryPartial[i]; + let foundMatch = true; + for(let j = 0; j < keys.length; ++j) { + let key = keys[j]; + if(partial[key] !== result[key]) { + foundMatch = false; + break; + } + } + if(foundMatch) { + objMatch = partial; + break; + } + } + + if(objMatch) { + newObj.total = result.total - objMatch.total; + newObj.total_employees = result.total; + newObj.total_teachers = objMatch.total + match.push(newObj); + } + }); + + return match; +} + +employeesApp.get('/', rqfSchool.parse(), (req, res, next) => { + req.allEmployees = {} + req.allTeacher = {} + + if ("school" in req.filter) { + req.sql.field('SUM(escola.num_funcionarios)', 'total') + .field("'Brasil'", 'name') + .field('escola.ano_censo', 'year') + .from('escola') + .group('escola.ano_censo') + .order('escola.ano_censo') + .where('(escola.situacao_de_funcionamento = 1) AND (escola.ensino_regular = 1 OR escola.ensino_eja = 1 OR escola.educacao_profissional = 1) AND (dependencia_adm_id = 2 OR dependencia_adm_id = 3 OR dependencia_adm_id = 4) AND (escola.id=' + req.filter.school + ')'); + delete req.filter.school; + next(); + } else { + req.sql.field('SUM(escola.num_funcionarios)', 'total') + .field("'Brasil'", 'name') + .field('escola.ano_censo', 'year') + .from('escola') + .group('escola.ano_censo') + .order('escola.ano_censo') + .where('(escola.situacao_de_funcionamento = 1) AND (escola.ensino_regular = 1 OR escola.ensino_eja = 1 OR escola.educacao_profissional = 1) AND (dependencia_adm_id = 2 OR dependencia_adm_id = 3 OR dependencia_adm_id = 4)'); + next(); + } +}, rqfSchool.build(), query, rqfSchool.parse(), id2str.transform(), (req, res, next) => { + + req.allEmployees = req.result; + req.resetSql(); + + if ("school" in req.filter) { + req.sql.field('SUM(docente_por_escola.total_professores)', 'total') + .field("'Brasil'", 'name') + .field('docente_por_escola.ano_censo', 'year') + .from('docente_por_escola') + .join('escola', null, 'docente_por_escola.escola_id=escola.id AND docente_por_escola.ano_censo=escola.ano_censo') + .group('docente_por_escola.ano_censo') + .order('docente_por_escola.ano_censo') + .where('(docente_por_escola.dependencia_adm_id > 1) AND (docente_por_escola.escola_id=' + req.filter.school + ')'); + } else if ("school" in req.dims) { + req.sql.field('SUM(docente_por_escola.total_professores)', 'total') + .field("'Brasil'", 'name') + .field('docente_por_escola.ano_censo', 'year') + .field('escola.nome_escola', 'school_name') + .from('docente_por_escola') + .join('escola', null, 'docente_por_escola.escola_id=escola.id AND docente_por_escola.ano_censo=escola.ano_censo') + .group('docente_por_escola.ano_censo') + .order('docente_por_escola.ano_censo') + .where('(docente_por_escola.dependencia_adm_id > 1)'); + } else { + req.sql.field('SUM(docente_por_escola.total_professores)', 'total') + .field("'Brasil'", 'name') + .field('docente_por_escola.ano_censo', 'year') + .from('docente_por_escola') + .group('docente_por_escola.ano_censo') + .order('docente_por_escola.ano_censo') + .where('(docente_por_escola.dependencia_adm_id > 1)'); + } + next(); + +}, rqfSchool.build(), query, id2str.transform(), (req, res, next) => { + + req.allTeacher = req.result; + let aux_employees = matchQueries(req.allEmployees, req.allTeacher); + req.result = aux_employees; + next(); +}, response('employees')); + +module.exports = employeesApp; diff --git a/src/libs/routes/financial.js b/src/libs/routes/financial.js new file mode 100644 index 0000000000000000000000000000000000000000..78c3b023f8991c64d813101c45cff2eeb62c468c --- /dev/null +++ b/src/libs/routes/financial.js @@ -0,0 +1,150 @@ +const express = require('express'); + +const financialApp = express.Router(); + +const libs = `${process.cwd()}/libs`; + +const log = require(`${libs}/log`)(module); + +const squel = require('squel'); + +const query = require(`${libs}/middlewares/query`).query; + +const response = require(`${libs}/middlewares/response`); + +const ReqQueryFields = require(`${libs}/middlewares/reqQueryFields`); + +const id2str = require(`${libs}/middlewares/id2str`); + +const addMissing = require(`${libs}/middlewares/addMissing`); + +const config = require(`${libs}/config`); + +const cache = require('apicache').options({ debug: config.debug, statusCodes: {include: [200]} }).middleware; + +let rqf = new ReqQueryFields(); + +financialApp.get('/year_range', (req, res, next) => { + req.sql.from('indicadores_financeiros') + .field('MIN(indicadores_financeiros.ano_censo)', 'start_year') + .field('MAX(indicadores_financeiros.ano_censo)', 'end_year'); + next(); +}, query, response('range')); + +financialApp.get('/years', (req, res, next) => { + req.sql.from('indicadores_financeiros') + .field('DISTINCT indicadores_financeiros.ano_censo', 'year'); + next(); +}, query, response('years')); + +financialApp.get('/sphere_adm', (req, res, next) => { + req.result = [ + {id: 1, name: "1"}, + {id: 2, name: "2"} + ] + next(); +}, response('sphere_adm')); + +financialApp.get('/financial_data', (req, res, next) => { + req.sql.from('indicadores_financeiros') + .field('DISTINCT indicadores_financeiros.dados_financeiros', 'financial_data'); + next(); +}, query, response('financial_data')); + +rqf.addField({ + name: 'filter', + field: false, + where: true +}).addField({ + name: 'dims', + field: true, + where: false +}).addValue({ + name: 'state', + table: 'estado', + tableField: ['sigla', 'id'], + resultField: ['sigla_uf', 'cod_uf'], + where: { + relation: '=', + type: 'integer', + field: 'estado_id', + table: 'indicadores_financeiros' + }, + join: { + primary: 'id', + foreign: 'estado_id', + foreignTable: 'indicadores_financeiros' + } +}).addValue({ + name: 'min_year', + table: 'indicadores_financeiros', + tableField: 'ano_censo', + resultField: 'year', + where: { + relation: '>=', + type: 'integer', + table: 'indicadores_financeiros', + field: 'ano_censo' + } +}).addValue({ + name: 'max_year', + table: 'indicadores_financeiros', + tableField: 'ano_censo', + resultField: 'year', + where: { + relation: '<=', + type: 'integer', + table: 'indicadores_financeiros', + field: 'ano_censo' + } +}).addValue({ + name: 'sphere_adm', + table: 'indicadores_financeiros', + tableField: 'esfera_adm', + resultField: 'sphere_adm_id', + where: { + relation: '=', + type: 'integer', + field: 'esfera_adm' + } +}).addValue({ + name: 'city', + table: 'indicadores_financeiros', + tableField: 'municipio_id', + resultField: 'city_id', + where: { + relation: '=', + type: 'integer', + field: 'municipio_id' + } +}).addValue({ + name: 'financial_data', + table: 'indicadores_financeiros', + tableField: 'dados_financeiros', + resultField: 'financial_data_id', + where: { + relation: '=', + type: 'integer', + field: 'dados_financeiros' + } +}); + +financialApp.get('/', rqf.parse(), rqf.build(), (req, res, next) => { + req.sql.from('indicadores_financeiros') + .field('indicadores_financeiros.estado_id', 'state_id') + .field('indicadores_financeiros.ano_censo', 'year') + .field('estado.sigla', 'state_abbreviation') + .field('indicadores_financeiros.valor', 'valor') + .field('indicadores_financeiros.esfera_adm', 'sphere_adm_id') + .field('indicadores_financeiros.dados_financeiros', 'financial_data_id') + .join('estado', null, 'indicadores_financeiros.estado_id=estado.id') + .group('indicadores_financeiros.ano_censo') + .group('indicadores_financeiros.estado_id') + .group('estado.sigla') + .group('indicadores_financeiros.valor') + .group('indicadores_financeiros.dados_financeiros') + .group('indicadores_financeiros.esfera_adm') + next(); +}, query, addMissing(rqf), id2str.transform(), response('financial')); + +module.exports = financialApp; diff --git a/src/libs/routes/school.js b/src/libs/routes/school.js index 830697742406491451539276261c468cc4024f04..3f4dd7141f6ce4c374969f37aaa5ee5335ee3498 100644 --- a/src/libs/routes/school.js +++ b/src/libs/routes/school.js @@ -60,6 +60,18 @@ schoolApp.get('/location', cache('15 day'), (req, res, next) => { next(); }, response('location')); +schoolApp.get('/rural_location', cache('15 day'), (req, res, next) => { + req.result = [ + {id: 1, name: "Urbana"}, + {id: 2, name: "Rural"}, + {id: 3, name: "Rural - Ãrea de assentamento"}, + {id: 4, name: "Rural - Terra indÃgena"}, + {id: 5, name: "Rural - Ãrea remanescente de quilombos"}, + {id: 6, name: "Rural - Unidade de uso sustentável"} + ]; + next(); +}, response('rural_location')); + schoolApp.get('/adm_dependency', (req, res, next) => { req.result = []; for(let i = 1; i <= 4; ++i) { @@ -359,6 +371,16 @@ rqfCount.addField({ type: 'integer', field: 'cod_localizacao' } +}).addValue({ + name: 'rural_location', + table: 'escola', + tableField: 'localidade_area_rural', + resultField: 'rural_location_id', + where: { + relation: '=', + type: 'integer', + field: 'localidade_area_rural' + } }).addValue({ name: 'adm_dependency', table: 'escola', @@ -402,52 +424,52 @@ rqfCount.addField({ }).addValue({ name: 'education_day_care_child', table: 'escola', - tableField: 'reg_infantil_creche', + tableField: 'reg_infantil_creche_t1', resultField: 'education_day_care_child_id', where: { relation: '=', type: 'boolean', - field: 'reg_infantil_creche' + field: 'reg_infantil_creche_t1' } }).addValue({ name: 'education_preschool_child', table: 'escola', - tableField: 'reg_infantil_preescola', + tableField: 'reg_infantil_preescola_t1', resultField: 'education_preschool_child_id', where: { relation: '=', type: 'boolean', - field: 'reg_infantil_preescola' + field: 'reg_infantil_preescola_t1' } }).addValue({ name: 'education_begin_elementary_school', table: 'escola', - tableField: 'reg_fund_ai', + tableField: 'reg_fund_ai_t1', resultField: 'education_begin_elementary_school_id', where: { relation: '=', type: 'boolean', - field: 'reg_fund_ai' + field: 'reg_fund_ai_t1' } }).addValue({ name: 'education_end_elementary_school', table: 'escola', - tableField: 'reg_fund_af', + tableField: 'reg_fund_af_t1', resultField: 'education_end_elementary_school_id', where: { relation: '=', type: 'boolean', - field: 'reg_fund_af' + field: 'reg_fund_af_t1' } }).addValue({ name: 'education_middle_school', table: 'escola', - tableField: 'reg_medio_medio', + tableField: 'reg_medio_medio_t1', resultField: 'education_middle_school_id', where: { relation: '=', type: 'boolean', - field: 'reg_medio_medio' + field: 'reg_medio_medio_t1' } }).addValue({ name: 'education_professional', diff --git a/src/libs/routes/transport.js b/src/libs/routes/transport.js index 449895d0c5ea618daf6114f7cf105de67ee3456e..409cb216c6cd62ea334df6eafce40c3f165dd7e0 100644 --- a/src/libs/routes/transport.js +++ b/src/libs/routes/transport.js @@ -83,17 +83,21 @@ transportApp.get('/rural_location', (req, res, next) => { next(); }, response('rural_location')); -transportApp.get('/education_level_basic', (req, res, next) => { +transportApp.get('/education_level_mod', (req, res, next) => { req.result = [ {id: null, name: 'Não classificada'}, {id: 1, name: 'Creche'}, {id: 2, name: 'Pré-Escola'}, {id: 4, name: 'Ensino Fundamental - anos iniciais'}, {id: 5, name: 'Ensino Fundamental - anos finais'}, - {id: 6, name: 'Ensino Médio'} + {id: 6, name: 'Ensino Médio'}, + {id: 7, name: 'Turmas multiseriadas e multietapas'}, + {id: 8, name: 'EJA - Ensino Fundamental'}, + {id: 9, name: 'EJA - Ensino Médio'}, + {id: 10, name: 'Educação Profissional'} ]; next(); -}, response('education_level_basic')); +}, response('education_level_mod')); transportApp.get('/service_type', (req, res, next) => { req.result = [ @@ -244,10 +248,10 @@ rqf.addField({ field: 'responsavel_transp' } }).addValue({ - name: 'education_level_basic', + name: 'education_level_mod', table: 'matricula', tableField: 'etapas_mod_ensino_segmento_id', - resultField: 'education_level_basic_id', + resultField: 'education_level_mod_id', where: { relation: '=', type: 'integer',