OLD | NEW |
1 // Copyright 2015 The Chromium Authors. All rights reserved. | 1 // Copyright 2015 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 // adapted from github.com/golang/appengine/datastore | 5 // adapted from github.com/golang/appengine/datastore |
6 | 6 |
7 package datastore | 7 package datastore |
8 | 8 |
9 import ( | 9 import ( |
10 "bytes" | 10 "bytes" |
(...skipping 561 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
572 func (i *IDParser) getFullID() string { | 572 func (i *IDParser) getFullID() string { |
573 return fmt.Sprintf("%s|%d", i.parent, i.id) | 573 return fmt.Sprintf("%s|%d", i.parent, i.id) |
574 } | 574 } |
575 | 575 |
576 func (i *IDParser) GetAllMeta() PropertyMap { | 576 func (i *IDParser) GetAllMeta() PropertyMap { |
577 pm := GetPLS(i).GetAllMeta() | 577 pm := GetPLS(i).GetAllMeta() |
578 pm.SetMeta("id", i.getFullID()) | 578 pm.SetMeta("id", i.getFullID()) |
579 return pm | 579 return pm |
580 } | 580 } |
581 | 581 |
582 func (i *IDParser) GetMeta(key string) (interface{}, error) { | 582 func (i *IDParser) GetMeta(key string) (interface{}, bool) { |
583 if key == "id" { | 583 if key == "id" { |
584 » » return i.getFullID(), nil | 584 » » return i.getFullID(), true |
585 } | 585 } |
586 return GetPLS(i).GetMeta(key) | 586 return GetPLS(i).GetMeta(key) |
587 } | 587 } |
588 | 588 |
589 func (i *IDParser) GetMetaDefault(key string, dflt interface{}) interface{} { | 589 func (i *IDParser) SetMeta(key string, value interface{}) bool { |
590 » return GetMetaDefaultImpl(i.GetMeta, key, dflt) | |
591 } | |
592 | |
593 func (i *IDParser) SetMeta(key string, value interface{}) (err error) { | |
594 if key == "id" { | 590 if key == "id" { |
595 // let the panics flooowwww | 591 // let the panics flooowwww |
596 vS := strings.SplitN(value.(string), "|", 2) | 592 vS := strings.SplitN(value.(string), "|", 2) |
597 i.parent = vS[0] | 593 i.parent = vS[0] |
| 594 var err error |
598 i.id, err = strconv.ParseInt(vS[1], 10, 64) | 595 i.id, err = strconv.ParseInt(vS[1], 10, 64) |
599 » » return | 596 » » if err != nil { |
| 597 » » » panic(err) |
| 598 » » } |
| 599 » » return true |
600 } | 600 } |
601 return GetPLS(i).SetMeta(key, value) | 601 return GetPLS(i).SetMeta(key, value) |
602 } | 602 } |
603 | 603 |
604 type KindOverride struct { | 604 type KindOverride struct { |
605 ID int64 `gae:"$id"` | 605 ID int64 `gae:"$id"` |
606 | 606 |
607 customKind string `gae:"-"` | 607 customKind string `gae:"-"` |
608 } | 608 } |
609 | 609 |
610 var _ MetaGetterSetter = (*KindOverride)(nil) | 610 var _ MetaGetterSetter = (*KindOverride)(nil) |
611 | 611 |
612 func (i *KindOverride) GetAllMeta() PropertyMap { | 612 func (i *KindOverride) GetAllMeta() PropertyMap { |
613 pm := GetPLS(i).GetAllMeta() | 613 pm := GetPLS(i).GetAllMeta() |
614 if i.customKind != "" { | 614 if i.customKind != "" { |
615 pm.SetMeta("kind", i.customKind) | 615 pm.SetMeta("kind", i.customKind) |
616 } | 616 } |
617 return pm | 617 return pm |
618 } | 618 } |
619 | 619 |
620 func (i *KindOverride) GetMeta(key string) (interface{}, error) { | 620 func (i *KindOverride) GetMeta(key string) (interface{}, bool) { |
621 if key == "kind" && i.customKind != "" { | 621 if key == "kind" && i.customKind != "" { |
622 » » return i.customKind, nil | 622 » » return i.customKind, true |
623 } | 623 } |
624 return GetPLS(i).GetMeta(key) | 624 return GetPLS(i).GetMeta(key) |
625 } | 625 } |
626 | 626 |
627 func (i *KindOverride) GetMetaDefault(key string, dflt interface{}) interface{}
{ | 627 func (i *KindOverride) SetMeta(key string, value interface{}) bool { |
628 » return GetMetaDefaultImpl(i.GetMeta, key, dflt) | |
629 } | |
630 | |
631 func (i *KindOverride) SetMeta(key string, value interface{}) error { | |
632 if key == "kind" { | 628 if key == "kind" { |
633 kind := value.(string) | 629 kind := value.(string) |
634 if kind != "KindOverride" { | 630 if kind != "KindOverride" { |
635 i.customKind = kind | 631 i.customKind = kind |
636 } else { | 632 } else { |
637 i.customKind = "" | 633 i.customKind = "" |
638 } | 634 } |
639 » » return nil | 635 » » return true |
640 } | 636 } |
641 » return ErrMetaFieldUnset | 637 » return GetPLS(i).SetMeta(key, value) |
642 } | 638 } |
643 | 639 |
644 type EmbeddedID struct { | 640 type EmbeddedID struct { |
645 Thing string | 641 Thing string |
646 Val int | 642 Val int |
647 } | 643 } |
648 | 644 |
649 var _ PropertyConverter = (*EmbeddedID)(nil) | 645 var _ PropertyConverter = (*EmbeddedID)(nil) |
650 | 646 |
651 func (e *EmbeddedID) ToProperty() (ret Property, err error) { | 647 func (e *EmbeddedID) ToProperty() (ret Property, err error) { |
(...skipping 963 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1615 | 1611 |
1616 checkErr := func(actual interface{}, expected string) bool { | 1612 checkErr := func(actual interface{}, expected string) bool { |
1617 if expected == "" { | 1613 if expected == "" { |
1618 So(actual, ShouldErrLike, nil) | 1614 So(actual, ShouldErrLike, nil) |
1619 } else { | 1615 } else { |
1620 So(actual, ShouldErrLike, expected) | 1616 So(actual, ShouldErrLike, expected) |
1621 } | 1617 } |
1622 return expected != "" | 1618 return expected != "" |
1623 } | 1619 } |
1624 | 1620 |
| 1621 getPLSErr := func(obj interface{}) (pls PropertyLoadSaver, err error) { |
| 1622 defer func() { |
| 1623 if v := recover(); v != nil { |
| 1624 err = v.(error) |
| 1625 } |
| 1626 }() |
| 1627 pls = GetPLS(obj) |
| 1628 return |
| 1629 } |
| 1630 |
1625 Convey("Test round-trip", t, func() { | 1631 Convey("Test round-trip", t, func() { |
1626 for _, tc := range testCases { | 1632 for _, tc := range testCases { |
1627 tc := tc | 1633 tc := tc |
1628 Convey(tc.desc, func() { | 1634 Convey(tc.desc, func() { |
1629 pls, ok := tc.src.(PropertyLoadSaver) | 1635 pls, ok := tc.src.(PropertyLoadSaver) |
1630 if !ok { | 1636 if !ok { |
1631 » » » » » pls = GetPLS(tc.src) | 1637 » » » » » var err error |
1632 » » » » } | 1638 » » » » » pls, err = getPLSErr(tc.src) |
1633 » » » » if checkErr(pls.Problem(), tc.plsErr) { | 1639 » » » » » if checkErr(err, tc.plsErr) { |
1634 » » » » » return | 1640 » » » » » » return |
| 1641 » » » » » } |
1635 } | 1642 } |
1636 So(pls, ShouldNotBeNil) | 1643 So(pls, ShouldNotBeNil) |
1637 | 1644 |
1638 savedProps, err := pls.Save(false) | 1645 savedProps, err := pls.Save(false) |
1639 if checkErr(err, tc.saveErr) { | 1646 if checkErr(err, tc.saveErr) { |
1640 return | 1647 return |
1641 } | 1648 } |
1642 So(savedProps, ShouldNotBeNil) | 1649 So(savedProps, ShouldNotBeNil) |
1643 | 1650 |
1644 var got interface{} | 1651 var got interface{} |
1645 if _, ok := tc.want.(PropertyMap); ok { | 1652 if _, ok := tc.want.(PropertyMap); ok { |
1646 pls = PropertyMap{} | 1653 pls = PropertyMap{} |
1647 got = pls | 1654 got = pls |
1648 } else { | 1655 } else { |
1649 got = reflect.New(reflect.TypeOf(tc.want
).Elem()).Interface() | 1656 got = reflect.New(reflect.TypeOf(tc.want
).Elem()).Interface() |
1650 if pls, ok = got.(PropertyLoadSaver); !o
k { | 1657 if pls, ok = got.(PropertyLoadSaver); !o
k { |
1651 » » » » » » pls = GetPLS(got) | 1658 » » » » » » var err error |
| 1659 » » » » » » pls, err = getPLSErr(got) |
| 1660 » » » » » » if checkErr(err, tc.plsLoadErr)
{ |
| 1661 » » » » » » » return |
| 1662 » » » » » » } |
1652 } | 1663 } |
1653 } | 1664 } |
1654 | 1665 |
1655 if checkErr(pls.Problem(), tc.plsLoadErr) { | |
1656 return | |
1657 } | |
1658 So(pls, ShouldNotBeNil) | 1666 So(pls, ShouldNotBeNil) |
1659 | 1667 |
1660 err = pls.Load(savedProps) | 1668 err = pls.Load(savedProps) |
1661 if checkErr(err, tc.loadErr) { | 1669 if checkErr(err, tc.loadErr) { |
1662 return | 1670 return |
1663 } | 1671 } |
1664 if tc.want == nil { | 1672 if tc.want == nil { |
1665 return | 1673 return |
1666 } | 1674 } |
1667 | 1675 |
1668 if gotT, ok := got.(*T); ok { | 1676 if gotT, ok := got.(*T); ok { |
1669 // Round tripping a time.Time can result
in a different time.Location: Local instead of UTC. | 1677 // Round tripping a time.Time can result
in a different time.Location: Local instead of UTC. |
1670 // We therefore test equality explicitly
, instead of relying on reflect.DeepEqual. | 1678 // We therefore test equality explicitly
, instead of relying on reflect.DeepEqual. |
1671 So(gotT.T.Equal(tc.want.(*T).T), ShouldB
eTrue) | 1679 So(gotT.T.Equal(tc.want.(*T).T), ShouldB
eTrue) |
1672 } else { | 1680 } else { |
1673 So(got, ShouldResemble, tc.want) | 1681 So(got, ShouldResemble, tc.want) |
1674 } | 1682 } |
1675 }) | 1683 }) |
1676 } | 1684 } |
1677 }) | 1685 }) |
1678 } | 1686 } |
1679 | 1687 |
1680 func TestMeta(t *testing.T) { | 1688 func TestMeta(t *testing.T) { |
1681 t.Parallel() | 1689 t.Parallel() |
1682 | 1690 |
1683 Convey("Test meta fields", t, func() { | 1691 Convey("Test meta fields", t, func() { |
1684 Convey("Can retrieve from struct", func() { | 1692 Convey("Can retrieve from struct", func() { |
1685 o := &N0{ID: 100} | 1693 o := &N0{ID: 100} |
1686 mgs := getMGS(o) | 1694 mgs := getMGS(o) |
1687 » » » val, err := mgs.GetMeta("id") | 1695 » » » val, ok := mgs.GetMeta("id") |
1688 » » » So(err, ShouldBeNil) | 1696 » » » So(ok, ShouldBeTrue) |
1689 So(val, ShouldEqual, 100) | 1697 So(val, ShouldEqual, 100) |
1690 | 1698 |
1691 » » » val, err = mgs.GetMeta("kind") | 1699 » » » val, ok = mgs.GetMeta("kind") |
1692 » » » So(err, ShouldBeNil) | 1700 » » » So(ok, ShouldBeTrue) |
1693 So(val, ShouldEqual, "whatnow") | 1701 So(val, ShouldEqual, "whatnow") |
1694 | 1702 |
1695 » » » So(mgs.GetMetaDefault("kind", "zappo"), ShouldEqual, "wh
atnow") | 1703 » » » So(GetMetaDefault(mgs, "kind", "zappo"), ShouldEqual, "w
hatnow") |
1696 » » » So(mgs.GetMetaDefault("id", "stringID"), ShouldEqual, "s
tringID") | 1704 » » » So(GetMetaDefault(mgs, "id", "stringID"), ShouldEqual, "
stringID") |
1697 » » » So(mgs.GetMetaDefault("id", 6), ShouldEqual, 100) | 1705 » » » So(GetMetaDefault(mgs, "id", 6), ShouldEqual, 100) |
1698 }) | 1706 }) |
1699 | 1707 |
1700 Convey("Getting something not there is an error", func() { | 1708 Convey("Getting something not there is an error", func() { |
1701 o := &N0{ID: 100} | 1709 o := &N0{ID: 100} |
1702 mgs := getMGS(o) | 1710 mgs := getMGS(o) |
1703 » » » _, err := mgs.GetMeta("wat") | 1711 » » » _, ok := mgs.GetMeta("wat") |
1704 » » » So(err, ShouldEqual, ErrMetaFieldUnset) | 1712 » » » So(ok, ShouldBeFalse) |
1705 }) | 1713 }) |
1706 | 1714 |
1707 Convey("Default works for missing fields", func() { | 1715 Convey("Default works for missing fields", func() { |
1708 o := &N0{ID: 100} | 1716 o := &N0{ID: 100} |
1709 mgs := getMGS(o) | 1717 mgs := getMGS(o) |
1710 » » » So(mgs.GetMetaDefault("whozit", 10), ShouldEqual, 10) | 1718 » » » So(GetMetaDefault(mgs, "whozit", 10), ShouldEqual, 10) |
1711 }) | 1719 }) |
1712 | 1720 |
1713 » » Convey("getting/setting from a bad struct is an error", func() { | 1721 » » Convey("getting mgs for bad struct is an error", func() { |
1714 » » » o := &Recursive{} | 1722 » » » So(func() { getMGS(&Recursive{}) }, ShouldPanicLike, |
1715 » » » mgs := getMGS(o) | 1723 » » » » `field "R" is recursively defined`) |
1716 » » » _, err := mgs.GetMeta("wat") | |
1717 » » » So(err, ShouldNotBeNil) | |
1718 | |
1719 » » » err = mgs.SetMeta("wat", 100) | |
1720 » » » So(err, ShouldNotBeNil) | |
1721 » » }) | |
1722 | |
1723 » » Convey("Default works for bad structs", func() { | |
1724 » » » o := &Recursive{} | |
1725 » » » mgs := getMGS(o) | |
1726 » » » So(mgs.GetMetaDefault("whozit", 10), ShouldEqual, 10) | |
1727 }) | 1724 }) |
1728 | 1725 |
1729 Convey("can assign values to exported meta fields", func() { | 1726 Convey("can assign values to exported meta fields", func() { |
1730 o := &N0{ID: 100} | 1727 o := &N0{ID: 100} |
1731 mgs := getMGS(o) | 1728 mgs := getMGS(o) |
1732 » » » err := mgs.SetMeta("id", int64(200)) | 1729 » » » So(mgs.SetMeta("id", int64(200)), ShouldBeTrue) |
1733 » » » So(err, ShouldBeNil) | |
1734 So(o.ID, ShouldEqual, 200) | 1730 So(o.ID, ShouldEqual, 200) |
1735 | |
1736 }) | 1731 }) |
1737 | 1732 |
1738 » » Convey("assigning to unsassiagnable fields is a simple error", f
unc() { | 1733 » » Convey("assigning to unsassiagnable fields returns !ok", func()
{ |
1739 o := &N0{ID: 100} | 1734 o := &N0{ID: 100} |
1740 mgs := getMGS(o) | 1735 mgs := getMGS(o) |
1741 » » » err := mgs.SetMeta("kind", "hi") | 1736 » » » So(mgs.SetMeta("kind", "hi"), ShouldBeFalse) |
1742 » » » So(err.Error(), ShouldContainSubstring, "unexported fiel
d") | 1737 » » » So(mgs.SetMeta("noob", "hi"), ShouldBeFalse) |
1743 | |
1744 » » » err = mgs.SetMeta("noob", "hi") | |
1745 » » » So(err, ShouldEqual, ErrMetaFieldUnset) | |
1746 }) | 1738 }) |
1747 }) | 1739 }) |
1748 | 1740 |
1749 Convey("StructPLS Miscellaneous", t, func() { | 1741 Convey("StructPLS Miscellaneous", t, func() { |
1750 Convey("a simple struct has a default $kind", func() { | 1742 Convey("a simple struct has a default $kind", func() { |
1751 So(GetPLS(&Simple{}).GetAllMeta(), ShouldResemble, Prope
rtyMap{ | 1743 So(GetPLS(&Simple{}).GetAllMeta(), ShouldResemble, Prope
rtyMap{ |
1752 "$kind": []Property{mpNI("Simple")}, | 1744 "$kind": []Property{mpNI("Simple")}, |
1753 }) | 1745 }) |
1754 }) | 1746 }) |
1755 | 1747 |
1756 Convey("multiple overlapping fields is an error", func() { | 1748 Convey("multiple overlapping fields is an error", func() { |
1757 o := &BadMeta{} | 1749 o := &BadMeta{} |
1758 » » » pls := GetPLS(o) | 1750 » » » So(func() { GetPLS(o) }, ShouldPanicLike, "multiple time
s") |
1759 » » » err := pls.Load(nil) | |
1760 » » » So(err, ShouldErrLike, "multiple times") | |
1761 » » » e := pls.Problem() | |
1762 » » » _, err = pls.Save(true) | |
1763 » » » So(err, ShouldEqual, e) | |
1764 » » » err = pls.Load(nil) | |
1765 » » » So(err, ShouldEqual, e) | |
1766 }) | 1751 }) |
1767 | 1752 |
1768 Convey("empty property names are invalid", func() { | 1753 Convey("empty property names are invalid", func() { |
1769 So(validPropertyName(""), ShouldBeFalse) | 1754 So(validPropertyName(""), ShouldBeFalse) |
1770 }) | 1755 }) |
1771 | 1756 |
1772 Convey("attempting to get a PLS for a non *struct is an error",
func() { | 1757 Convey("attempting to get a PLS for a non *struct is an error",
func() { |
1773 » » » pls := GetPLS((*[]string)(nil)) | 1758 » » » So(func() { GetPLS((*[]string)(nil)) }, ShouldPanicLike, |
1774 » » » So(pls.Problem(), ShouldEqual, ErrInvalidEntityType) | 1759 » » » » "cannot GetPLS(*[]string): not a pointer-to-stru
ct") |
1775 | |
1776 » » » Convey("the error PLS can still be used", func() { | |
1777 » » » » k, _ := pls.GetMeta("kind") | |
1778 » » » » So(k, ShouldBeNil) | |
1779 | |
1780 » » » » props := pls.GetAllMeta() | |
1781 » » » » So(props, ShouldResemble, PropertyMap{ | |
1782 » » » » » "$kind": []Property{mpNI("")}, | |
1783 » » » » }) | |
1784 | |
1785 » » » » _, err := pls.Save(true) | |
1786 » » » » So(err, ShouldNotBeNil) | |
1787 » » » }) | |
1788 }) | 1760 }) |
1789 | 1761 |
1790 Convey("convertible meta default types", func() { | 1762 Convey("convertible meta default types", func() { |
1791 type OKDefaults struct { | 1763 type OKDefaults struct { |
1792 When string `gae:"$when,tomorrow"` | 1764 When string `gae:"$when,tomorrow"` |
1793 Amount int64 `gae:"$amt,100"` | 1765 Amount int64 `gae:"$amt,100"` |
1794 DoIt Toggle `gae:"$doit,on"` | 1766 DoIt Toggle `gae:"$doit,on"` |
1795 } | 1767 } |
1796 okd := &OKDefaults{} | 1768 okd := &OKDefaults{} |
1797 pls := GetPLS(okd) | |
1798 mgs := getMGS(okd) | 1769 mgs := getMGS(okd) |
1799 So(pls.Problem(), ShouldBeNil) | |
1800 | 1770 |
1801 » » » v, err := mgs.GetMeta("when") | 1771 » » » v, ok := mgs.GetMeta("when") |
1802 » » » So(err, ShouldBeNil) | 1772 » » » So(ok, ShouldBeTrue) |
1803 So(v, ShouldEqual, "tomorrow") | 1773 So(v, ShouldEqual, "tomorrow") |
1804 | 1774 |
1805 » » » v, err = mgs.GetMeta("amt") | 1775 » » » v, ok = mgs.GetMeta("amt") |
1806 » » » So(err, ShouldBeNil) | 1776 » » » So(ok, ShouldBeTrue) |
1807 So(v, ShouldEqual, int64(100)) | 1777 So(v, ShouldEqual, int64(100)) |
1808 | 1778 |
1809 So(okd.DoIt, ShouldEqual, Auto) | 1779 So(okd.DoIt, ShouldEqual, Auto) |
1810 » » » v, err = mgs.GetMeta("doit") | 1780 » » » v, ok = mgs.GetMeta("doit") |
1811 » » » So(err, ShouldBeNil) | 1781 » » » So(ok, ShouldBeTrue) |
1812 So(v, ShouldBeTrue) | 1782 So(v, ShouldBeTrue) |
1813 | 1783 |
1814 » » » err = mgs.SetMeta("doit", false) | 1784 » » » So(mgs.SetMeta("doit", false), ShouldBeTrue) |
1815 » » » So(err, ShouldBeNil) | 1785 » » » v, ok = mgs.GetMeta("doit") |
1816 » » » v, err = mgs.GetMeta("doit") | 1786 » » » So(ok, ShouldBeTrue) |
1817 » » » So(err, ShouldBeNil) | |
1818 So(v, ShouldBeFalse) | 1787 So(v, ShouldBeFalse) |
1819 So(okd.DoIt, ShouldEqual, Off) | 1788 So(okd.DoIt, ShouldEqual, Off) |
1820 | 1789 |
1821 » » » err = mgs.SetMeta("doit", true) | 1790 » » » So(mgs.SetMeta("doit", true), ShouldBeTrue) |
1822 » » » So(err, ShouldBeNil) | 1791 » » » v, ok = mgs.GetMeta("doit") |
1823 » » » v, err = mgs.GetMeta("doit") | 1792 » » » So(ok, ShouldBeTrue) |
1824 » » » So(err, ShouldBeNil) | |
1825 So(v, ShouldBeTrue) | 1793 So(v, ShouldBeTrue) |
1826 So(okd.DoIt, ShouldEqual, On) | 1794 So(okd.DoIt, ShouldEqual, On) |
1827 | 1795 |
1828 Convey("Toggle fields REQUIRE a default", func() { | 1796 Convey("Toggle fields REQUIRE a default", func() { |
1829 type BadToggle struct { | 1797 type BadToggle struct { |
1830 Bad Toggle `gae:"$wut"` | 1798 Bad Toggle `gae:"$wut"` |
1831 } | 1799 } |
1832 » » » » pls := GetPLS(&BadToggle{}) | 1800 » » » » So(func() { GetPLS(&BadToggle{}) }, ShouldPanicL
ike, "bad/missing default") |
1833 » » » » So(pls.Problem().Error(), ShouldContainSubstring
, "bad/missing default") | |
1834 }) | 1801 }) |
1835 }) | 1802 }) |
1836 | 1803 |
1837 Convey("meta fields can be saved", func() { | 1804 Convey("meta fields can be saved", func() { |
1838 type OKDefaults struct { | 1805 type OKDefaults struct { |
1839 When string `gae:"$when,tomorrow"` | 1806 When string `gae:"$when,tomorrow"` |
1840 Amount int64 `gae:"$amt,100"` | 1807 Amount int64 `gae:"$amt,100"` |
1841 } | 1808 } |
1842 pls := GetPLS(&OKDefaults{}) | 1809 pls := GetPLS(&OKDefaults{}) |
1843 pm, err := pls.Save(true) | 1810 pm, err := pls.Save(true) |
1844 So(err, ShouldBeNil) | 1811 So(err, ShouldBeNil) |
1845 So(pm, ShouldResemble, PropertyMap{ | 1812 So(pm, ShouldResemble, PropertyMap{ |
1846 "$when": {mpNI("tomorrow")}, | 1813 "$when": {mpNI("tomorrow")}, |
1847 "$amt": {mpNI(100)}, | 1814 "$amt": {mpNI(100)}, |
1848 "$kind": {mpNI("OKDefaults")}, | 1815 "$kind": {mpNI("OKDefaults")}, |
1849 }) | 1816 }) |
1850 | 1817 |
1851 » » » v, err := pm.GetMeta("when") | 1818 » » » v, ok := pm.GetMeta("when") |
1852 » » » So(err, ShouldBeNil) | 1819 » » » So(ok, ShouldBeTrue) |
1853 So(v, ShouldEqual, "tomorrow") | 1820 So(v, ShouldEqual, "tomorrow") |
1854 | 1821 |
1855 » » » v, err = pm.GetMeta("amt") | 1822 » » » v, ok = pm.GetMeta("amt") |
1856 » » » So(err, ShouldBeNil) | 1823 » » » So(ok, ShouldBeTrue) |
1857 So(v, ShouldEqual, int64(100)) | 1824 So(v, ShouldEqual, int64(100)) |
1858 }) | 1825 }) |
1859 | 1826 |
1860 Convey("default are optional", func() { | 1827 Convey("default are optional", func() { |
1861 type OverrideDefault struct { | 1828 type OverrideDefault struct { |
1862 Val int64 `gae:"$val"` | 1829 Val int64 `gae:"$val"` |
1863 } | 1830 } |
1864 o := &OverrideDefault{} | 1831 o := &OverrideDefault{} |
1865 mgs := getMGS(o) | 1832 mgs := getMGS(o) |
1866 | 1833 |
1867 » » » v, err := mgs.GetMeta("val") | 1834 » » » v, ok := mgs.GetMeta("val") |
1868 » » » So(err, ShouldBeNil) | 1835 » » » So(ok, ShouldBeTrue) |
1869 So(v, ShouldEqual, int64(0)) | 1836 So(v, ShouldEqual, int64(0)) |
1870 }) | 1837 }) |
1871 | 1838 |
1872 Convey("overridable defaults", func() { | 1839 Convey("overridable defaults", func() { |
1873 type OverrideDefault struct { | 1840 type OverrideDefault struct { |
1874 Val int64 `gae:"$val,100"` | 1841 Val int64 `gae:"$val,100"` |
1875 } | 1842 } |
1876 o := &OverrideDefault{} | 1843 o := &OverrideDefault{} |
1877 mgs := getMGS(o) | 1844 mgs := getMGS(o) |
1878 | 1845 |
1879 » » » v, err := mgs.GetMeta("val") | 1846 » » » v, ok := mgs.GetMeta("val") |
1880 » » » So(err, ShouldBeNil) | 1847 » » » So(ok, ShouldBeTrue) |
1881 So(v, ShouldEqual, int64(100)) | 1848 So(v, ShouldEqual, int64(100)) |
1882 | 1849 |
1883 o.Val = 10 | 1850 o.Val = 10 |
1884 » » » v, err = mgs.GetMeta("val") | 1851 » » » v, ok = mgs.GetMeta("val") |
1885 » » » So(err, ShouldBeNil) | 1852 » » » So(ok, ShouldBeTrue) |
1886 So(v, ShouldEqual, int64(10)) | 1853 So(v, ShouldEqual, int64(10)) |
1887 }) | 1854 }) |
1888 | 1855 |
1889 Convey("Derived metadata fields", func() { | 1856 Convey("Derived metadata fields", func() { |
1890 type DerivedString string | 1857 type DerivedString string |
1891 type DerivedInt int16 | 1858 type DerivedInt int16 |
1892 type DerivedStruct struct { | 1859 type DerivedStruct struct { |
1893 ID DerivedString `gae:"$id"` | 1860 ID DerivedString `gae:"$id"` |
1894 Foo DerivedInt `gae:"$foo"` | 1861 Foo DerivedInt `gae:"$foo"` |
1895 } | 1862 } |
1896 o := &DerivedStruct{"hello", 10} | 1863 o := &DerivedStruct{"hello", 10} |
1897 mgs := getMGS(o) | 1864 mgs := getMGS(o) |
1898 » » » v, err := mgs.GetMeta("id") | 1865 » » » v, ok := mgs.GetMeta("id") |
1899 » » » So(err, ShouldBeNil) | 1866 » » » So(ok, ShouldBeTrue) |
1900 So(v, ShouldEqual, "hello") | 1867 So(v, ShouldEqual, "hello") |
1901 | 1868 |
1902 » » » v, err = mgs.GetMeta("foo") | 1869 » » » v, ok = mgs.GetMeta("foo") |
1903 » » » So(err, ShouldBeNil) | 1870 » » » So(ok, ShouldBeTrue) |
1904 So(v, ShouldEqual, int64(10)) | 1871 So(v, ShouldEqual, int64(10)) |
1905 | 1872 |
1906 » » » So(mgs.SetMeta("id", "nerds"), ShouldBeNil) | 1873 » » » So(mgs.SetMeta("id", "nerds"), ShouldBeTrue) |
1907 » » » So(mgs.SetMeta("foo", 20), ShouldBeNil) | 1874 » » » So(mgs.SetMeta("foo", 20), ShouldBeTrue) |
1908 So(o.ID, ShouldEqual, DerivedString("nerds")) | 1875 So(o.ID, ShouldEqual, DerivedString("nerds")) |
1909 So(o.Foo, ShouldEqual, DerivedInt(20)) | 1876 So(o.Foo, ShouldEqual, DerivedInt(20)) |
1910 }) | 1877 }) |
1911 | 1878 |
1912 Convey("Bad default meta type", func() { | 1879 Convey("Bad default meta type", func() { |
1913 type BadDefault struct { | 1880 type BadDefault struct { |
1914 Val time.Time `gae:"$meta,tomorrow"` | 1881 Val time.Time `gae:"$meta,tomorrow"` |
1915 } | 1882 } |
1916 » » » pls := GetPLS(&BadDefault{}) | 1883 » » » So(func() { GetPLS(&BadDefault{}) }, ShouldPanicLike, "b
ad type") |
1917 » » » So(pls.Problem().Error(), ShouldContainSubstring, "bad t
ype") | |
1918 }) | 1884 }) |
1919 | 1885 |
1920 Convey("MetaGetterSetter implementation (IDParser)", func() { | 1886 Convey("MetaGetterSetter implementation (IDParser)", func() { |
1921 idp := &IDParser{parent: "moo", id: 100} | 1887 idp := &IDParser{parent: "moo", id: 100} |
1922 mgs := getMGS(idp) | 1888 mgs := getMGS(idp) |
1923 » » » So(mgs.GetMetaDefault("id", ""), ShouldEqual, "moo|100") | 1889 » » » So(GetMetaDefault(mgs, "id", ""), ShouldEqual, "moo|100"
) |
1924 » » » So(mgs.GetMetaDefault("kind", ""), ShouldEqual, "CoolKin
d") | |
1925 | 1890 |
1926 » » » So(mgs.SetMeta("kind", "Something"), ShouldErrLike, "une
xported field") | 1891 » » » So(GetMetaDefault(mgs, "kind", ""), ShouldEqual, "CoolKi
nd") |
1927 » » » So(mgs.SetMeta("id", "happy|27"), ShouldBeNil) | 1892 |
| 1893 » » » So(mgs.SetMeta("kind", "Something"), ShouldBeFalse) |
| 1894 » » » So(mgs.SetMeta("id", "happy|27"), ShouldBeTrue) |
1928 | 1895 |
1929 So(idp.parent, ShouldEqual, "happy") | 1896 So(idp.parent, ShouldEqual, "happy") |
1930 So(idp.id, ShouldEqual, 27) | 1897 So(idp.id, ShouldEqual, 27) |
1931 | 1898 |
1932 So(mgs.GetAllMeta(), ShouldResemble, PropertyMap{ | 1899 So(mgs.GetAllMeta(), ShouldResemble, PropertyMap{ |
1933 "$id": {mpNI("happy|27")}, | 1900 "$id": {mpNI("happy|27")}, |
1934 "$kind": {mpNI("CoolKind")}, | 1901 "$kind": {mpNI("CoolKind")}, |
1935 }) | 1902 }) |
1936 }) | 1903 }) |
1937 | 1904 |
1938 Convey("MetaGetterSetter implementation (KindOverride)", func()
{ | 1905 Convey("MetaGetterSetter implementation (KindOverride)", func()
{ |
1939 ko := &KindOverride{ID: 20} | 1906 ko := &KindOverride{ID: 20} |
1940 mgs := getMGS(ko) | 1907 mgs := getMGS(ko) |
1941 » » » So(mgs.GetMetaDefault("kind", ""), ShouldEqual, "KindOve
rride") | 1908 » » » So(GetMetaDefault(mgs, "kind", ""), ShouldEqual, "KindOv
erride") |
1942 | 1909 |
1943 ko.customKind = "something" | 1910 ko.customKind = "something" |
1944 » » » So(mgs.GetMetaDefault("kind", ""), ShouldEqual, "somethi
ng") | 1911 » » » So(GetMetaDefault(mgs, "kind", ""), ShouldEqual, "someth
ing") |
1945 | 1912 |
1946 » » » So(mgs.SetMeta("kind", "Nerp"), ShouldBeNil) | 1913 » » » So(mgs.SetMeta("kind", "Nerp"), ShouldBeTrue) |
1947 So(ko.customKind, ShouldEqual, "Nerp") | 1914 So(ko.customKind, ShouldEqual, "Nerp") |
1948 | 1915 |
1949 » » » So(mgs.SetMeta("kind", "KindOverride"), ShouldBeNil) | 1916 » » » So(mgs.SetMeta("kind", "KindOverride"), ShouldBeTrue) |
1950 So(ko.customKind, ShouldEqual, "") | 1917 So(ko.customKind, ShouldEqual, "") |
1951 | 1918 |
1952 So(mgs.GetAllMeta(), ShouldResemble, PropertyMap{ | 1919 So(mgs.GetAllMeta(), ShouldResemble, PropertyMap{ |
1953 "$id": {mpNI(20)}, | 1920 "$id": {mpNI(20)}, |
1954 "$kind": {mpNI("KindOverride")}, | 1921 "$kind": {mpNI("KindOverride")}, |
1955 }) | 1922 }) |
1956 ko.customKind = "wut" | 1923 ko.customKind = "wut" |
1957 So(mgs.GetAllMeta(), ShouldResemble, PropertyMap{ | 1924 So(mgs.GetAllMeta(), ShouldResemble, PropertyMap{ |
1958 "$id": {mpNI(20)}, | 1925 "$id": {mpNI(20)}, |
1959 "$kind": {mpNI("wut")}, | 1926 "$kind": {mpNI("wut")}, |
1960 }) | 1927 }) |
1961 | 1928 |
1962 props, err := GetPLS(ko).Save(true) | 1929 props, err := GetPLS(ko).Save(true) |
1963 So(err, ShouldBeNil) | 1930 So(err, ShouldBeNil) |
1964 So(props, ShouldResemble, PropertyMap{ | 1931 So(props, ShouldResemble, PropertyMap{ |
1965 "$id": {mpNI(20)}, | 1932 "$id": {mpNI(20)}, |
1966 "$kind": {mpNI("wut")}, | 1933 "$kind": {mpNI("wut")}, |
1967 }) | 1934 }) |
1968 }) | 1935 }) |
1969 | 1936 |
1970 Convey("Embeddable Metadata structs", func() { | 1937 Convey("Embeddable Metadata structs", func() { |
1971 ide := &IDEmbedder{EmbeddedID{"hello", 10}} | 1938 ide := &IDEmbedder{EmbeddedID{"hello", 10}} |
1972 pls := GetPLS(ide) | 1939 pls := GetPLS(ide) |
1973 » » » val, err := pls.GetMeta("id") | 1940 » » » val, ok := pls.GetMeta("id") |
1974 » » » So(err, ShouldBeNil) | 1941 » » » So(ok, ShouldBeTrue) |
1975 So(val, ShouldEqual, "hello|10") | 1942 So(val, ShouldEqual, "hello|10") |
1976 | 1943 |
1977 » » » So(pls.SetMeta("id", "sup|1337"), ShouldBeNil) | 1944 » » » So(pls.SetMeta("id", "sup|1337"), ShouldBeTrue) |
1978 So(ide.EmbeddedID, ShouldResemble, EmbeddedID{"sup", 133
7}) | 1945 So(ide.EmbeddedID, ShouldResemble, EmbeddedID{"sup", 133
7}) |
1979 | 1946 |
1980 So(pls.GetAllMeta(), ShouldResembleV, PropertyMap{ | 1947 So(pls.GetAllMeta(), ShouldResembleV, PropertyMap{ |
1981 "$id": {mpNI("sup|1337")}, | 1948 "$id": {mpNI("sup|1337")}, |
1982 "$kind": {mpNI("IDEmbedder")}, | 1949 "$kind": {mpNI("IDEmbedder")}, |
1983 }) | 1950 }) |
1984 }) | 1951 }) |
1985 }) | 1952 }) |
1986 } | 1953 } |
OLD | NEW |