3

Problem :

File downloaded using the request module, and written it to the file system is differnt to the one directly downloaded using the browser

I am fetching a font file located at https://assets.ajio.com/static/assets/ec86819f634b9e9979b83bae65b170dd.woff. there are the following 3 cases.

Case 1

Now when normally the website runs this URL from its source code, the following is the response [as checked in deveoper tools]

d09GRgABAAAAAPqMABMAAAACNCgAAQAyAAAAAAAAAAAAAAAAAAAAAAAAAABCQVN....

and when I fetch it using my nodejs script, I get the response

wOFF....??....4(...2....

The above was the response I saw in browser's developer's tools network tab.

Case 2

But when I run both the urls i.e. the original and my own http://<host>/_oe/https://assets.ajio.com/static/assets/ec86819f634b9e9979b83bae65b170dd.woff, in Postman, I get the same response.

Case 3

Then again when copy and paste https://assets.ajio.com/static/assets/ec86819f634b9e9979b83bae65b170dd.woff in a broswer, the file which downloads reads like

774f 4646 0001 0000 0000 c7f4 000b 0000 0000 c7a8 0001 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000 4f53 2f32

and the file which gets written using my nodejs script reads like

774f 4646 0001 0000 0000 efbf bdef bfbd 000b 0000 0000 c7a8 0001 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000

Both are again different.

Question

My question is, can anyone explain whats going on here, what am I doing wrong, and what can I do to get the correct font file with correct encoding so that it is used correctly on the frontend.

Nodejs script : Here's my code of nodejs

app.get('/*', (req, res) => {
    var extension = '.woff';
    var options         = {
        headers: {
            'connection': 'keep-alive',
            'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:60.0) Gecko/20100101 Firefox/60.0',
            'Accept-Language': 'en-US,en;q=0.5'
        },
        url: 'https://assets.ajio.com/static/assets/ec86819f634b9e9979b83bae65b170dd.woff'
    };

    sendRequest(options, extension, function(headers){

        //setting response headers
        var header_ = {};
        for(var attribute in  headers){
            if(attribute !== 'content-length'){
                header_[attribute] = headers[attribute];
            }
        }

        //#================================================================
        res.writeHead(200, header_);
        var filePath = path.join(__dirname, 'output/temp'+extension);
            var stat = fileSystem.statSync(filePath);
            var readStream = fileSystem.createReadStream(filePath);
            //read from `readStream` write to `res`
            readStream.pipe(res);
        //#================================================================

    });

})

async function sendRequest(options, extension, callback){
    var headers;
    request(options, function(error, response, body){
        if (!error && response.statusCode == 200) {
            headers = response.headers;

            if (String(response.headers['content-type']).indexOf('text/html') !== -1){
                // any manipulation related to the html file                
            }else {
                // where I get my font url response
                fileSystem.writeFile(path.join(__dirname, 'output/temp'+extension), body, function(err) {
                    if(err) {
                        return console.log(err);
                    }
                    callback(headers);
                }); 
            }
        }
    });
}

app.listen(3000, () => console.log('Example app listening on port 3000!'));

UPDATE

I have even used "binary" option while writing file i.e.

fileSystem.writeFile(path.join(__dirname, 'output/temp'+extension), body, "binary", function(err) {})

Now on console I get data in the required format d09GRgABAAAAAP39AAs...

but still different from what I get from the original website i.e. d09GRgABAAAAAPqMABMAAAACNC...

Tripti Rawat
  • 645
  • 7
  • 19
  • Why do you think that `d09GRgABAAAAAPqMABMAA` and `wOFF....??` are different? The first one is the base64 representation of the data and often used if the content that has to be displayed is binary. – t.niese Jun 19 '18 at 06:13
  • Pls read the last part of question (Update). Now I am using the binary encoding to write file and i am getting base64 representation as u suggested, but still they both are different. They both meaning one I get from my nodejs script and one I get from the original website @t.niese – Tripti Rawat Jun 19 '18 at 06:22
  • Possible duplicate of [Why Node.js failed to serve .woff files](https://stackoverflow.com/questions/13372997/why-node-js-failed-to-serve-woff-files) – Paul Jun 19 '18 at 06:36
  • I read the whole question. If you ask a question you should first write what problem you have. Somethign like: `File downloaded using the request module, and written it to the file system is differnt to the one directly downloaded using the browser`. Adding those overservatiosn is great, but you should help the read to understand the problem first. – t.niese Jun 19 '18 at 06:38
  • @Paul don't know about the question but the answer specified there I have already mentioned in my question that it is not working. So could be different context. Thanks – Tripti Rawat Jun 19 '18 at 06:38
  • @t.niese got it. Thanks for the suggestion – Tripti Rawat Jun 19 '18 at 06:39

1 Answers1

2

To get the raw buffer for the response, you would need to set encoding to null

var options = {
    url: 'https://assets.ajio.com/static/assets/ec86819f634b9e9979b83bae65b170dd.woff',
    encoding : null
};

If you then write this to a file:

request(options, function(error, response, body) {
    fs.writeFile('test.woff', body, function(err) {

    })
})

Then this will be equl to the one you requested.

t.niese
  • 39,256
  • 9
  • 74
  • 101