Ha dattiloscritto fornire un'API pubblica esplicita per NodeJS Modulo di accesso?

voti
11

Dall'interno di un'applicazione nodo vorrei fare:

var typeScript = require('typescript'); 

typeScript.compile('...')

Sto cercando di implementare il compilatore in un sistema di compilazione, ma senza accesso a un API pubblica (typescript.compile, ecc) questo è impossibile.

Ecco un esempio più completo di quello che vorrei fare, anche se il sotto è per LiveScript, non tipografico, utilitized in un plugin scritto per il sistema di build-Brunch.io:

LiveScript = require 'LiveScript'
sysPath = require 'path'

module.exports = class LiveScriptCompiler
  brunchPlugin: yes
  type: 'javascript'
  extension: 'ls'

  constructor: (@config) ->
    null

  compile: (data, path, callback) ->
    try
      result = LiveScript.compile data, bare: yes
    catch err
      error = err
    finally
      callback error, result

  include: [
    (sysPath.join __dirname, '..', 'vendor', 'prelude-browser-0.6.0.js')
  ]

Curioso di sapere se qualcuno ha trovato un work-around?

Aggiornare

Ho finito per attuare la mia soluzione a una serie di problemi sopra elencati e altrove. Si prega di consultare https://github.com/damassi/TypeScript-Watcher per ulteriori informazioni e l'utilizzo.

È pubblicato 03/10/2012 alle 22:40
fonte dall'utente
In altre lingue...                            


5 risposte

voti
8

Questo è un po 'hacky ma funzionerà.

Ho pensato a questo stesso proprio ieri e stavo controllando il loro codice. Se si seleziona bin / typscript.js dal loro codice sorgente (Si tratta di un file molto grande, con quasi 21k righe di codice), si vedrà crea TypeScript.TypeScriptCompiler, e allora vi accorgerete che questo non esporre un modo di compilazione .

var compiler = new TypeScript.TypeScriptCompiler(outfile, errorfile, 
    new TypeScript.NullLogger(), settings);

Ora, è necessario un modo semplice per esporlo. Per fare questo, sarà necessario modificare il loro codice, che è il motivo per cui questo è hacky. Per fare questo, è possibile modificare typescript.js con l'aggiunta di:

module.exports = exports = TypeScript;

Proprio alla fine del file.

Quindi, è possibile creare un file index.js nella radice del modulo (avviso: installare il modulo in un ambito locale per tutto questo: "NPM installare dattiloscritto"), che espone l'oggetto.

exports.TypeScript = require("bin/typescript");

E pronto! Ora si può solo chiamare e compilare il codice di utilizzarlo. È possibile controllare come utilizzare l'API per la compilazione nel file tsc.js.

Mi scuso in anticipo per il codice orribile avanti:

var fs = require("fs");
var TypeScript = require("typescript");
var path = "test.ts";
var pathout = "test.js";
var content = fs.readFileSync(path, "utf-8");
var fd = fs.openSync(pathout, 'w'); 
var outFile = { 
    Write: function (str) { 
        fs.writeSync(fd, str); 
    }, 
    WriteLine: function (str) {
    console.log(fd, str); 
        fs.writeSync(fd, str + '\r\n'); 
    }, 
    Close: function () { 
        fs.closeSync(fd); 
        fd = null; 
    } 
};
var createFile = function (path) { 
    function mkdirRecursiveSync(path) { 
        var stats = fs.statSync(path); 
        if(stats.isFile()) { 
            throw "\"" + path + "\" exists but isn't a directory."; 
        } else { 
            if(stats.isDirectory()) { 
                return; 
            } else { 
                mkdirRecursiveSync(_path.dirname(path)); 
                fs.mkdirSync(path, 509); 
            } 
        } 
    } 
    mkdirRecursiveSync(_path.dirname(path));
    console.log(path) 
    var fd = fs.openSync(path, 'w'); 
    return { 
        Write: function (str) { 
            fs.writeSync(fd, str); 
        }, 
        WriteLine: function (str) { 
            fs.writeSync(fd, str + '\r\n'); 
        }, 
        Close: function () { 
            fs.closeSync(fd); 
            fd = null; 
        } 
    }; 
};
var stderr = { 
    Write: function (str) { 
        process.stderr.write(str); 
    }, 
    WriteLine: function (str) { 
        process.stderr.write(str + '\n'); 
    }, 
    Close: function () { 
    } 
}
var compiler = new TypeScript.TypeScriptCompiler(outFile, outFile);
compiler.setErrorOutput(stderr);
compiler.addUnit(content, path);
compiler.typeCheck();
compiler.emit(false, createFile);
outFile.Close();

Per qualche ragione chi ha scritto il codice è stato un vero fan di C # e ha proceduto ad andare avanti e di utilizzare metodi chiama WriteLine, Close e scrittura, che sono in realtà solo involucri. Si potrebbe ottenere questo del sovraccarico di dover aggiungere queste funzioni, ma si dovrà modificare un sacco di codice nel modulo e non è valsa la pena. Penso che è meglio avere una classe di estendere (o se siete ancora in JS, ereditano il prototipo) e lasciar fare per voi, per fare asciugare.

Qualcosa di veramente bello è che se si desidera tradurre 500 file dattiloscritto e metterli tutti in un unico file .js, si può chiamare compiler.addUnit (anothercontent, anotherpath); 500 volte e poi vedere andare tutto in un unico file :)

Concentrandosi su cose meglio: se controlli tsc.js codice, si trova una classe del compilatore batch. Se si desidera che questo per un processo di compilazione, potrebbe essere meglio usare qualcosa di più robusto simile. Esso fornisce i file guardare e altro ancora.

Dopo aver sfogliato il codice, penso che mi limiterò a presentare un biglietto per il team di sviluppo e chiedere loro di fornire un'API chiara ¬¬

Nota: Tutti i file di legge qui sono fatte in modo sincrono. Questo è male, molto male, in termini di prestazioni. Non so esattamente che cosa avete intenzione di fare, ma non potrei raccomandare più che trovare un modo per rendere questo asincrona, se possibile.

Risposto il 03/10/2012 a 23:52
fonte dall'utente

voti
2

Al momento non è possibile realizzare una compilation soltanto con un richiedono e chiamando compilare. Se si riesce a guardare ai harness.ts c'è un modulo compilatore che fornisce un modo piuttosto semplice di farlo, ma vorrei suggerire di chiamare TSC esternamente.

///<reference path='node.d.ts'/>
import exec = module('child_process');

var child = exec.exec('tsc foo.ts',
  function (error, stdout, stderr) {
    if (error !== null) {
      console.log('exec error: ' + error);
    }
});

Credo che questo sarebbe fare il lavoro.

Risposto il 03/10/2012 a 23:01
fonte dall'utente

voti
1

Si potrebbe provare https://github.com/sinclairzx81/typescript.api . Questo progetto fa la roba estensione require (), ma ha anche alcune funzionalità per compilare ts fonte manualmente. Dovrebbe essere possibile creare un sistema di compilazione automatica con esso.

notare tho suo costruita sul compilatore dattiloscritto 0.9, in modo che può o non può avere successo la compilazione 0.8.3 sorgente dato diversi aggiornamenti della lingua.

Risposto il 13/05/2013 a 12:03
fonte dall'utente

voti
1

meglio richiedono potrebbe aiutare a raggiungere questo obiettivo, se invece si sta eseguendo / accesso al file dattiloscritto.

Esso consente di require () file dattiloscritto - senza pre-compilazione necessario - e un sacco di altri formati di file (CoffeeScript, ClojureScript, YAML, XML, etc.)

require('better-require')();
var myModule = require('./mymodule.ts');

Disclosure: ho scritto meglio richiedono.

Risposto il 01/11/2012 a 16:06
fonte dall'utente

voti
1

Controllare questo progetto github da niutech, è possibile convertire il codice dattiloscritto in codice JS al volo in del browser , ma penso che può essere facilmente essere modificato per lavorare in node.js.

Risposto il 07/10/2012 a 07:41
fonte dall'utente

Cookies help us deliver our services. By using our services, you agree to our use of cookies. Learn more