Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
28 changes: 13 additions & 15 deletions Angular5-csv.spec.ts → AngularCsv.spec.ts
Original file line number Diff line number Diff line change
@@ -1,17 +1,16 @@
/* tslint:disable:no-unused-variable */

import {Angular5Csv, CsvConfigConsts} from './Angular5-csv';

describe('Component: Angular2Csv', () => {
import { AngularCsv, CsvConfigConsts } from './AngularCsv';

describe('Component: AngularCsv', () => {

it('should create an file with name My_Report.csv', () => {
let component = new Angular5Csv([{name: 'test', age: 20}], 'My Report');
let component = new AngularCsv([{name: 'test', age: 20}], 'My Report');
expect(component).toBeTruthy();
});

it('should return correct order', () => {
let component = new Angular5Csv([{name: 'test', age: 20}], 'My Report', {useBom: false});
let component = new AngularCsv([{name: 'test', age: 20}], 'My Report', {useBom: false});
let csv = component['csv'];
let csv_rows = csv.split(CsvConfigConsts.EOL);
let first_row = csv_rows[0].replace(/"/g, '').split(',');
Expand All @@ -20,28 +19,28 @@ describe('Component: Angular2Csv', () => {
});

it('should return csv with title', () => {
let component = new Angular5Csv([{name: 'test', age: 20}], 'My Report', {showTitle: true, useBom: false});
let component = new AngularCsv([{name: 'test', age: 20}], 'My Report', {showTitle: true, useBom: false});
let csv = component['csv'];
let title = csv.split(CsvConfigConsts.EOL)[0];
expect(title).toEqual('My Report');
});

it('should return csv file with custom field separator', () => {
let component = new Angular5Csv([{name: 'test', age: 20}], 'My Report', {useBom: false, fieldSeparator: ';'});
let component = new AngularCsv([{name: 'test', age: 20}], 'My Report', {useBom: false, fieldSeparator: ';'});
let csv = component['csv'];
let first_row = csv.split(CsvConfigConsts.EOL)[0];
expect(first_row.split(';').length).toBe(2);
});

it('should return csv file with custom field separator', () => {
let component = new Angular5Csv([{name: 'test', age: 20}], 'My Report', {useBom: false, quoteStrings: '|'});
it('should return csv file with custom quote strings', () => {
let component = new AngularCsv([{name: 'test', age: 20}], 'My Report', {useBom: false, quoteStrings: '|'});
let csv = component['csv'];
let first_row = csv.split(CsvConfigConsts.EOL)[0].split(',');
expect(first_row[0]).toMatch('\\|.*\\|');
});

it('should return csv file with correct header labels', () => {
let component = new Angular5Csv([{name: 'test', age: 20}], 'My Report', {
let component = new AngularCsv([{name: 'test', age: 20}], 'My Report', {
useBom: false,
showLabels: true,
headers: ["name", "age"]
Expand All @@ -52,13 +51,12 @@ describe('Component: Angular2Csv', () => {
expect(labels[1]).toEqual('age');
});

it('should return nulls as empty strings if the options is selected', () => {
let component = new Angular5Csv([{name: null, age: null}], 'My Report', {useBom: false, nullToEmptyString: true});
it('should return nulls as empty strings if the option is selected', () => {
let component = new AngularCsv([{name: null, age: null}], 'My Report', {useBom: false, nullToEmptyString: true});
let csv = component['csv'];
let csv_rows = csv.split(CsvConfigConsts.EOL);
let first_row = csv_rows[0].replace(/"/g, '').split(',');
expect(first_row[0]).toEqual('');
expect(first_row[1]).toBe('');

})
});
});
});
110 changes: 31 additions & 79 deletions Angular5-csv.ts → AngularCsv.ts
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,7 @@ export const ConfigDefaults: Options = {
nullToEmptyString: CsvConfigConsts.DEFAULT_NULL_TO_EMPTY_STRING
};

export class Angular5Csv {
export class AngularCsv {

public fileName: string;
public labels: Array<String>;
Expand All @@ -55,11 +55,11 @@ export class Angular5Csv {
private csv = "";

constructor(DataJSON: any, filename: string, options?: any) {
let config = options || {};
const config = options || {};

this.data = typeof DataJSON != 'object' ? JSON.parse(DataJSON) : DataJSON;
this.data = typeof DataJSON !== 'object' ? JSON.parse(DataJSON) : DataJSON;

this._options = objectAssign({}, ConfigDefaults, config);
this._options = Object.assign({}, ConfigDefaults, config);

if (this._options.filename) {
this._options.filename = filename;
Expand All @@ -83,47 +83,41 @@ export class Angular5Csv {
this.getHeaders();
this.getBody();

if (this.csv == '') {
if (this.csv === '') {
console.log("Invalid data");
return;
}

if(this._options.noDownload) {
if (this._options.noDownload) {
return this.csv;
}

let blob = new Blob([this.csv], {"type": "text/csv;charset=utf8;"});
const blob = new Blob([this.csv], { type: "text/csv;charset=utf8;" });
const uri = URL.createObjectURL(blob);
const link = document.createElement("a");

if (navigator.msSaveBlob) {
let filename = this._options.filename.replace(/ /g, "_") + ".csv";
navigator.msSaveBlob(blob, filename);
} else {
let uri = 'data:attachment/csv;charset=utf-8,' + encodeURI(this.csv);
let link = document.createElement("a");
link.href = uri;
link.setAttribute('visibility', 'hidden');
link.download = this._options.filename.replace(/ /g, "_") + ".csv";

link.href = URL.createObjectURL(blob);

link.setAttribute('visibility', 'hidden');
link.download = this._options.filename.replace(/ /g, "_") + ".csv";

document.body.appendChild(link);
link.click();
document.body.removeChild(link);
}
document.body.appendChild(link);
link.click();
document.body.removeChild(link);
URL.revokeObjectURL(uri);
}

/**
* Create Headers
*/
getHeaders(): void {
if (this._options.headers.length > 0) {
const { headers } = this._options;
let row = headers.reduce((headerRow, header) => {
return headerRow + header + this._options.fieldSeparator;
}, '');
row = row.slice(0, -1);
this.csv += row + CsvConfigConsts.EOL;
}
if (this._options.headers.length > 0) {
const { headers } = this._options;
let row = headers.reduce((headerRow, header) => {
return headerRow + header + this._options.fieldSeparator;
}, '');
row = row.slice(0, -1);
this.csv += row + CsvConfigConsts.EOL;
}
}

/**
Expand All @@ -147,11 +141,11 @@ export class Angular5Csv {
*/
formatData(data: any) {

if (this._options.decimalseparator === 'locale' && Angular5Csv.isFloat(data)) {
if (this._options.decimalseparator === 'locale' && AngularCsv.isFloat(data)) {
return data.toLocaleString();
}

if (this._options.decimalseparator !== '.' && Angular5Csv.isFloat(data)) {
if (this._options.decimalseparator !== '.' && AngularCsv.isFloat(data)) {
return data.toString().replace('.', this._options.decimalseparator);
}

Expand All @@ -164,12 +158,12 @@ export class Angular5Csv {
}

if (this._options.nullToEmptyString) {
if(data === null) {
return data = '';
if (data === null) {
return '';
}
return data;
}

if (typeof data === 'boolean') {
return data ? 'TRUE' : 'FALSE';
}
Expand All @@ -185,47 +179,5 @@ export class Angular5Csv {
}
}

let hasOwnProperty = Object.prototype.hasOwnProperty;
let propIsEnumerable = Object.prototype.propertyIsEnumerable;

/**
* Convet to Object
* @param {any} val
*/
function toObject(val: any) {
if (val === null || val === undefined) {
throw new TypeError('Object.assign cannot be called with null or undefined');
}
return Object(val);
}

/**
* Assign data to new Object
* @param {any} target
* @param {any[]} ...source
*/
function objectAssign(target: any, ...source: any[]) {
let from: any;
let to = toObject(target);
let symbols: any;

for (let s = 1; s < arguments.length; s++) {
from = Object(arguments[s]);

for (const key in from) {
if (hasOwnProperty.call(from, key)) {
to[key] = from[key];
}
}

if ((<any>Object).getOwnPropertySymbols) {
symbols = (<any>Object).getOwnPropertySymbols(from);
for (let i = 0; i < symbols.length; i++) {
if (propIsEnumerable.call(from, symbols[i])) {
to[symbols[i]] = from[symbols[i]];
}
}
}
}
return to;
}
/** @deprecated Use AngularCsv instead */
export { AngularCsv as Angular5Csv };
104 changes: 55 additions & 49 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,28 +1,24 @@
![angularjs_logo](https://user-images.githubusercontent.com/4659608/37036392-9bf53686-2160-11e8-95fc-bbab638d7d60.png)
![angular_csv_logo](https://user-images.githubusercontent.com/4659608/37036392-9bf53686-2160-11e8-95fc-bbab638d7d60.png)

# Angular5-csv | Export to CSV in Angular5
# angular-csv | Export to CSV in Angular


[![Codacy Badge](https://api.codacy.com/project/badge/Grade/e2133aa828054d7c865563b50100eb8b)](https://www.codacy.com/app/me_101/angular5-csv?utm_source=github.com&amp;utm_medium=referral&amp;utm_content=alhazmy13/angular5-csv&amp;utm_campaign=Badge_Grade)
[![Build Status](https://travis-ci.org/alhazmy13/angular5-csv.svg?branch=master)](https://travis-ci.org/alhazmy13/angular5-csv)
[![npm version](https://badge.fury.io/js/angular5-csv.svg)](https://badge.fury.io/js/angular5-csv)
[![GitHub license](https://img.shields.io/github/license/alhazmy13/angular5-csv.svg)](https://github.com/alhazmy13/angular5-csv)
![Angular](https://img.shields.io/badge/Angular-%3E%3D5.0-red.svg)
![npm](https://img.shields.io/npm/dm/angular5-csv.svg)
[![Build Status](https://travis-ci.org/ehsanshrz/angular-csv.svg?branch=master)](https://travis-ci.org/ehsanshrz/angular-csv)
[![npm version](https://badge.fury.io/js/angular-csv.svg)](https://badge.fury.io/js/angular-csv)
[![GitHub license](https://img.shields.io/github/license/ehsanshrz/angular-csv.svg)](https://github.com/ehsanshrz/angular-csv)

> A helper library for creating CSV files in Angular5.
>
> A helper library for creating CSV files in Angular.

## Installation
## Installation

```javascript
npm install --save angular5-csv
```bash
npm install --save angular-csv
```

## Example
```javascript
## Example

import { Angular5Csv } from 'angular5-csv/dist/Angular5-csv';
```javascript
import { AngularCsv } from 'angular-csv/dist/AngularCsv';

var data = [
{
Expand All @@ -48,49 +44,59 @@ var data = [
},
];

new Angular5Csv(data, 'My Report');

new AngularCsv(data, 'My Report');
```

## API | **Angular5Csv(data, filename, options)**
## API | **AngularCsv(data, filename, options)**

| Option | Default | Description |
| :------------------ |:-----------:| -----|
| **fieldSeparator** | , | Defines the field separator character |
| **quoteStrings** | " | If provided, will use this character to "escape" fields, otherwise will use double quotes as default |
| **decimalseparator**| . | Defines the decimal separator character (default is `.`). If set to `"locale"`, it uses the [language sensitive representation of the number](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Number/toLocaleString). |
| **showLabels** | false | If provided, uses this attribute to create a header row |
| **showTitle** | false | If true, adds the title as the first row of the CSV |
| **title** | My Report | The title to use when `showTitle` is true |
| **useBom** | true | If true, adds a BOM character at the start of the CSV |
| **noDownload** | false | If true, disables automatic download and returns only the formatted CSV string |
| **headers** | [] | Array of column headers |
| **nullToEmptyString**| false | If true, all null values will be changed to empty strings |

## Options Example

| Option | Default | Description |
| :------------- |:-------------:| -----|
| **fieldSeparator** | , | Defines the field separator character |
| **quoteStrings** | " | If provided, will use this characters to "escape" fields, otherwise will use double quotes as deafult |
| **decimalseparator** | . | Defines the decimal separator character (default is .). If set to "locale", it uses the [language sensitive representation of the number](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Number/toLocaleString).|
| **showLabels** | false | If provided, would use this attribute to create a header row |
| **showTitle** | false | |
| **useBom** | true | If true, adds a BOM character at the start of the CSV |
| **noDownload** | false | If true, disables automatic download and returns only formatted CSV |
| **nullToEmptyString** | false | If true, all null values will be changed to empty strings |
```javascript
var options = {
fieldSeparator: ',',
quoteStrings: '"',
decimalseparator: '.',
showLabels: true,
showTitle: true,
title: 'Your title',
useBom: true,
noDownload: true,
headers: ["First Name", "Last Name", "ID"],
nullToEmptyString: true,
};

new AngularCsv(data, filename, options);
```

## Migration from angular5-csv

## Options Example
If you were using `angular5-csv`, replace your imports:

```javascript
var options = {
fieldSeparator: ',',
quoteStrings: '"',
decimalseparator: '.',
showLabels: true,
showTitle: true,
title: 'Your title',
useBom: true,
noDownload: true,
headers: ["First Name", "Last Name", "ID"],
nullToEmptyString: true,
};

Angular5Csv(data, filename, options);
// Before
import { Angular5Csv } from 'angular5-csv/dist/Angular5-csv';

// After
import { AngularCsv } from 'angular-csv/dist/AngularCsv';
```

## Credits

The `Angular5Csv` class is still exported as a deprecated alias for backwards compatibility.

## Credits

* [sn123](https://github.com/sn123)
* [arf1980](https://github.com/arf1980)
* [rob-moore](https://github.com/rob-moore)
* [sn123](https://github.com/sn123)
* [arf1980](https://github.com/arf1980)
* [rob-moore](https://github.com/rob-moore)
4 changes: 2 additions & 2 deletions karma.conf.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,8 @@ var configuration = {
frameworks: ["jasmine", "karma-typescript"],

files: [
'Angular5-csv.spec.ts',
'Angular5-csv.ts'
'AngularCsv.spec.ts',
'AngularCsv.ts'
],

preprocessors: {
Expand Down
Loading