Empresas
Empleos
  • Sobre nosotros
  • Soluciones
    • Publicación de vacantes
      Publica tu vacante y recibe candidatos calificados en 48h.
    • Evaluación de candidatos
      500+ pruebas técnicas y psicológicas, más anti-fraude.
    • Headhunting
      Búsqueda ejecutiva a la medida de principio a fin.
    • Nómina + EOR
      Dispersión de nómina y EOR en más de 15 países de LATAM.
  • Precios
  • Empleos

0

470
Vistas
Knex: combine varias funciones de puntos en una sola

¿Cómo puedo combinar múltiples funciones de puntos knex en una función de puntos grandes?

Por ejemplo tengo esta consulta:

 await knex .from(common) .select('x','y') .innerJoin(table1, `${table2}.id`, `${table1}.table2_id`) .whereNull(`${table1}.date`) .whereNull(`${table1}.file`) .where({ field1: 1, field2: 2 })

Las declaraciones de unión interna y whereNull son comunes a algunas otras consultas. ¿Es posible extraer esta parte?

 .innerJoin(table1, `${table2}.id`, `${table1}.table2_id`) .whereNull(`${table1}.date`) .whereNull(`${table1}.file`)

y reemplácelo con una función, .joinWhereNull .

Entonces la consulta original podría reescribirse así:

 await knex .from(common) .select('x','y') .joinWhereNull() .where({ field1: 1, field2: 2 })

He intentado escribir funciones personalizadas como esta

 const joinWhereNull = () => { return (query) => { return query .innerJoin(table1, `${table2}.id`, `${table1}.table2_id`) .whereNull(`${table1}.date`) .whereNull(`${table1}.file`) } }

Sin embargo, esto se siente torpe de usar y descubrí que la declaración de select también necesita su propia función, de lo contrario, se llama prematuramente.

¿Hay una manera más fácil de combinar funciones knex?

Editar También intenté usar un QueryBuilder personalizado:

 Knex.QueryBuilder.extend('joinWhereNull', function (table1, table2) { return this .innerJoin(table1, `${table2}.id`, `${table1}.table2_id`) .whereNull(`${table1}.date`) .whereNull(`${table1}.file`) })

Sin embargo, aparece un error de tipo que indica que joinwherenull no es una función.

about 4 years ago · Juan Pablo Isaza
2 Respuestas
Responde la pregunta

0

Puede utilizar el enfoque de QueryBuilder como se muestra aquí: Ampliación del Generador de consultas .

Sin embargo, TypeScript dará un error de tipo a menos que amplíe la interfaz de joinWhereNull con la función joinWhereNull. Las instrucciones para hacerlo están en la misma página: Ampliación del generador de consultas .

Citando aquí:

  1. Cree un archivo knex.d.ts dentro de una carpeta @types (o cualquier otra carpeta).
 // knex.d.ts import { Knex as KnexOriginal } from 'knex'; declare module 'knex' { namespace Knex { interface QueryBuilder { customSelect<TRecord, TResult>(value: number): KnexOriginal.QueryBuilder<TRecord, TResult>; } } }
  1. Agregue la nueva carpeta @types a typeRoots en su tsconfig.json.
 // tsconfig.json { "compilerOptions": { "typeRoots": [ "node_modules/@types", "@types" ], } }
about 4 years ago · Juan Pablo Isaza Denunciar

0

Lamentablemente, hay varias instancias de QueryBuilder en juego. Por lo tanto, definir el nuevo método en una instancia no funciona. Podemos establecer el nuevo método en QueryBuilder.prototype para que esté disponible en todas las instancias.

El siguiente código funcionó en mi entorno de prueba:

 const knex = require('knex')({ client: 'sqlite3', connection: { filename: './mydb.sqlite' }}); let common = 'common'; let table1 = 'table1'; let table2 = 'table2'; let field1 = 'field1'; let field2 = 'field2'; // using default methods console.log('one: ', knex .from(common) .select('x', 'y') .innerJoin(table1, `${table2}.id`, `${table1}.table2_id`) .whereNull(`${table1}.date`) .whereNull(`${table1}.file`) .where({ field1: 1, field2: 2, }) .toString() ); // define the new method //knex.queryBuilder().__proto__['joinWhereNull'] = function () { Object.getPrototypeOf(knex.queryBuilder())['joinWhereNull'] = function () { return this.innerJoin(table1, `${table2}.id`, `${table1}.table2_id`) .whereNull(`${table1}.date`) .whereNull(`${table1}.file`); }; // using our method console.log('two: ', knex .from(common) .select('x', 'y') .joinWhereNull() .where({ field1: 3, field2: 4, }) .toString() );

Producción:

 one: select `x`, `y` from `common` inner join `table1` on `table2`.`id` = `table1`.`table2_id` where `table1`.`date` is null and `table1`.`file` is null and `field1` = 1 and `field2` = 2 two: select `x`, `y` from `common` inner join `table1` on `table2`.`id` = `table1`.`table2_id` where `table1`.`date` is null and `table1`.`file` is null and `field1` = 3 and `field2` = 4

No tengo mucha idea de cómo funciona internamente la biblioteca. Pero encontré el siguiente comentario en el código:
hacer-knex.js

 // Allow chaining methods from the root object, before // any other information is specified. // // TODO: `QueryBuilder.extend(..)` allows new QueryBuilder // methods to be introduced via external components. // As a side-effect, it also pushes the new method names // into the `QueryInterface` array. // // The Problem: due to the way the code is currently // structured, these new methods cannot be retroactively // injected into existing `knex` instances! As a result, // some `knex` instances will support the methods, and // others will not. // // We should revisit this once we figure out the desired // behavior / usage. For instance: do we really want to // allow external components to directly manipulate `knex` // data structures? Or, should we come up w/ a different // approach that avoids side-effects / mutation? // // (FYI: I noticed this issue because I attempted to integrate // this logic directly into the `KNEX_PROPERTY_DEFINITIONS` // construction. However, `KNEX_PROPERTY_DEFINITIONS` is // constructed before any `knex` instances are created. // As a result, the method extensions were missing from all // `knex` instances.)
about 4 years ago · Juan Pablo Isaza Denunciar
Responde la pregunta
Encuentra empleos remotos

¡Descubre la nueva forma de encontrar empleo!

Top de empleos
Top categorías de empleo
Empresas
Publicar vacante Precios Comercial
Legal
Términos y condiciones Política de privacidad
© 2026 PeakU Inc. All Rights Reserved.
Andres GPT
Recomiéndame algunas ofertas
Necesito ayuda