|
1 |
| -// These tests check that the Schema operates correctly. |
2 | 1 | var Config = require('../src/Config');
|
3 | 2 | var Schema = require('../src/Schema');
|
4 | 3 | var dd = require('deep-diff');
|
5 | 4 |
|
6 | 5 | var config = new Config('test');
|
7 | 6 |
|
| 7 | +var hasAllPODobject = () => { |
| 8 | + var obj = new Parse.Object('HasAllPOD'); |
| 9 | + obj.set('aNumber', 5); |
| 10 | + obj.set('aString', 'string'); |
| 11 | + obj.set('aBool', true); |
| 12 | + obj.set('aDate', new Date()); |
| 13 | + obj.set('aObject', {k1: 'value', k2: true, k3: 5}); |
| 14 | + obj.set('aArray', ['contents', true, 5]); |
| 15 | + obj.set('aGeoPoint', new Parse.GeoPoint({latitude: 0, longitude: 0})); |
| 16 | + obj.set('aFile', new Parse.File('f.txt', { base64: 'V29ya2luZyBhdCBQYXJzZSBpcyBncmVhdCE=' })); |
| 17 | + var objACL = new Parse.ACL(); |
| 18 | + objACL.setPublicWriteAccess(false); |
| 19 | + obj.setACL(objACL); |
| 20 | + return obj; |
| 21 | +}; |
| 22 | + |
8 | 23 | describe('Schema', () => {
|
9 | 24 | it('can validate one object', (done) => {
|
10 | 25 | config.database.loadSchema().then((schema) => {
|
@@ -406,4 +421,153 @@ describe('Schema', () => {
|
406 | 421 | done();
|
407 | 422 | });
|
408 | 423 | });
|
| 424 | + |
| 425 | + it('can check if a class exists', done => { |
| 426 | + config.database.loadSchema() |
| 427 | + .then(schema => { |
| 428 | + return schema.addClassIfNotExists('NewClass', {}) |
| 429 | + .then(() => { |
| 430 | + schema.hasClass('NewClass') |
| 431 | + .then(hasClass => { |
| 432 | + expect(hasClass).toEqual(true); |
| 433 | + done(); |
| 434 | + }) |
| 435 | + .catch(fail); |
| 436 | + |
| 437 | + schema.hasClass('NonexistantClass') |
| 438 | + .then(hasClass => { |
| 439 | + expect(hasClass).toEqual(false); |
| 440 | + done(); |
| 441 | + }) |
| 442 | + .catch(fail); |
| 443 | + }) |
| 444 | + .catch(error => { |
| 445 | + fail('Couldn\'t create class'); |
| 446 | + fail(error); |
| 447 | + }); |
| 448 | + }) |
| 449 | + .catch(error => fail('Couldn\'t load schema')); |
| 450 | + }); |
| 451 | + |
| 452 | + it('refuses to delete fields from invalid class names', done => { |
| 453 | + config.database.loadSchema() |
| 454 | + .then(schema => schema.deleteField('fieldName', 'invalid class name')) |
| 455 | + .catch(error => { |
| 456 | + expect(error.code).toEqual(Parse.Error.INVALID_CLASS_NAME); |
| 457 | + done(); |
| 458 | + }); |
| 459 | + }); |
| 460 | + |
| 461 | + it('refuses to delete invalid fields', done => { |
| 462 | + config.database.loadSchema() |
| 463 | + .then(schema => schema.deleteField('invalid field name', 'ValidClassName')) |
| 464 | + .catch(error => { |
| 465 | + expect(error.code).toEqual(Parse.Error.INVALID_KEY_NAME); |
| 466 | + done(); |
| 467 | + }); |
| 468 | + }); |
| 469 | + |
| 470 | + it('refuses to delete the default fields', done => { |
| 471 | + config.database.loadSchema() |
| 472 | + .then(schema => schema.deleteField('installationId', '_Installation')) |
| 473 | + .catch(error => { |
| 474 | + expect(error.code).toEqual(136); |
| 475 | + expect(error.error).toEqual('field installationId cannot be changed'); |
| 476 | + done(); |
| 477 | + }); |
| 478 | + }); |
| 479 | + |
| 480 | + it('refuses to delete fields from nonexistant classes', done => { |
| 481 | + config.database.loadSchema() |
| 482 | + .then(schema => schema.deleteField('field', 'NoClass')) |
| 483 | + .catch(error => { |
| 484 | + expect(error.code).toEqual(Parse.Error.INVALID_CLASS_NAME); |
| 485 | + expect(error.error).toEqual('class NoClass does not exist'); |
| 486 | + done(); |
| 487 | + }); |
| 488 | + }); |
| 489 | + |
| 490 | + it('refuses to delete fields that dont exist', done => { |
| 491 | + hasAllPODobject().save() |
| 492 | + .then(() => config.database.loadSchema()) |
| 493 | + .then(schema => schema.deleteField('missingField', 'HasAllPOD')) |
| 494 | + .fail(error => { |
| 495 | + expect(error.code).toEqual(255); |
| 496 | + expect(error.error).toEqual('field missingField does not exist, cannot delete'); |
| 497 | + done(); |
| 498 | + }); |
| 499 | + }); |
| 500 | + |
| 501 | + it('drops related collection when deleting relation field', done => { |
| 502 | + var obj1 = hasAllPODobject(); |
| 503 | + obj1.save() |
| 504 | + .then(savedObj1 => { |
| 505 | + var obj2 = new Parse.Object('HasPointersAndRelations'); |
| 506 | + obj2.set('aPointer', savedObj1); |
| 507 | + var relation = obj2.relation('aRelation'); |
| 508 | + relation.add(obj1); |
| 509 | + return obj2.save(); |
| 510 | + }) |
| 511 | + .then(() => { |
| 512 | + config.database.db.collection('test__Join:aRelation:HasPointersAndRelations', { strict: true }, (err, coll) => { |
| 513 | + expect(err).toEqual(null); |
| 514 | + config.database.loadSchema() |
| 515 | + .then(schema => schema.deleteField('aRelation', 'HasPointersAndRelations', config.database.db, 'test_')) |
| 516 | + .then(() => config.database.db.collection('test__Join:aRelation:HasPointersAndRelations', { strict: true }, (err, coll) => { |
| 517 | + expect(err).not.toEqual(null); |
| 518 | + done(); |
| 519 | + })) |
| 520 | + }); |
| 521 | + }) |
| 522 | + }); |
| 523 | + |
| 524 | + it('can delete string fields and resave as number field', done => { |
| 525 | + Parse.Object.disableSingleInstance(); |
| 526 | + var obj1 = hasAllPODobject(); |
| 527 | + var obj2 = hasAllPODobject(); |
| 528 | + var p = Parse.Object.saveAll([obj1, obj2]) |
| 529 | + .then(() => config.database.loadSchema()) |
| 530 | + .then(schema => schema.deleteField('aString', 'HasAllPOD', config.database.db, 'test_')) |
| 531 | + .then(() => new Parse.Query('HasAllPOD').get(obj1.id)) |
| 532 | + .then(obj1Reloaded => { |
| 533 | + expect(obj1Reloaded.get('aString')).toEqual(undefined); |
| 534 | + obj1Reloaded.set('aString', ['not a string', 'this time']); |
| 535 | + obj1Reloaded.save() |
| 536 | + .then(obj1reloadedAgain => { |
| 537 | + expect(obj1reloadedAgain.get('aString')).toEqual(['not a string', 'this time']); |
| 538 | + return new Parse.Query('HasAllPOD').get(obj2.id); |
| 539 | + }) |
| 540 | + .then(obj2reloaded => { |
| 541 | + expect(obj2reloaded.get('aString')).toEqual(undefined); |
| 542 | + done(); |
| 543 | + Parse.Object.enableSingleInstance(); |
| 544 | + }); |
| 545 | + }) |
| 546 | + }); |
| 547 | + |
| 548 | + it('can delete pointer fields and resave as string', done => { |
| 549 | + Parse.Object.disableSingleInstance(); |
| 550 | + var obj1 = new Parse.Object('NewClass'); |
| 551 | + obj1.save() |
| 552 | + .then(() => { |
| 553 | + obj1.set('aPointer', obj1); |
| 554 | + return obj1.save(); |
| 555 | + }) |
| 556 | + .then(obj1 => { |
| 557 | + expect(obj1.get('aPointer').id).toEqual(obj1.id); |
| 558 | + }) |
| 559 | + .then(() => config.database.loadSchema()) |
| 560 | + .then(schema => schema.deleteField('aPointer', 'NewClass', config.database.db, 'test_')) |
| 561 | + .then(() => new Parse.Query('NewClass').get(obj1.id)) |
| 562 | + .then(obj1 => { |
| 563 | + expect(obj1.get('aPointer')).toEqual(undefined); |
| 564 | + obj1.set('aPointer', 'Now a string'); |
| 565 | + return obj1.save(); |
| 566 | + }) |
| 567 | + .then(obj1 => { |
| 568 | + expect(obj1.get('aPointer')).toEqual('Now a string'); |
| 569 | + done(); |
| 570 | + Parse.Object.enableSingleInstance(); |
| 571 | + }); |
| 572 | + }); |
409 | 573 | });
|
0 commit comments