@@ -22,6 +22,7 @@ import (
22
22
"time"
23
23
24
24
"github.com/google/go-cmp/cmp"
25
+ "github.com/google/go-cmp/cmp/cmpopts"
25
26
"github.com/tektoncd/pipeline/pkg/apis/config"
26
27
cfgtesting "github.com/tektoncd/pipeline/pkg/apis/config/testing"
27
28
"github.com/tektoncd/pipeline/pkg/apis/pipeline/pod"
@@ -31,6 +32,7 @@ import (
31
32
corev1resources "k8s.io/apimachinery/pkg/api/resource"
32
33
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
33
34
"knative.dev/pkg/apis"
35
+ duckv1 "knative.dev/pkg/apis/duck/v1"
34
36
)
35
37
36
38
func TestPipelineRun_Invalid (t * testing.T ) {
@@ -1511,3 +1513,180 @@ func TestPipelineRunSpecBetaFeatures(t *testing.T) {
1511
1513
})
1512
1514
}
1513
1515
}
1516
+
1517
+ func TestPipelineRunSpec_ValidateUpdate (t * testing.T ) {
1518
+ tests := []struct {
1519
+ name string
1520
+ isCreate bool
1521
+ isUpdate bool
1522
+ baselinePipelineRun * v1.PipelineRun
1523
+ pipelineRun * v1.PipelineRun
1524
+ expectedError apis.FieldError
1525
+ }{
1526
+ {
1527
+ name : "is create ctx" ,
1528
+ pipelineRun : & v1.PipelineRun {
1529
+ Spec : v1.PipelineRunSpec {},
1530
+ },
1531
+ isCreate : true ,
1532
+ isUpdate : false ,
1533
+ expectedError : apis.FieldError {},
1534
+ }, {
1535
+ name : "is update ctx, no changes" ,
1536
+ baselinePipelineRun : & v1.PipelineRun {
1537
+ Spec : v1.PipelineRunSpec {
1538
+ Status : "" ,
1539
+ },
1540
+ },
1541
+ pipelineRun : & v1.PipelineRun {
1542
+ Spec : v1.PipelineRunSpec {
1543
+ Status : "" ,
1544
+ },
1545
+ },
1546
+ isCreate : false ,
1547
+ isUpdate : true ,
1548
+ expectedError : apis.FieldError {},
1549
+ }, {
1550
+ name : "is update ctx, baseline is nil, skip validation" ,
1551
+ baselinePipelineRun : nil ,
1552
+ pipelineRun : & v1.PipelineRun {
1553
+ Spec : v1.PipelineRunSpec {
1554
+ Timeouts : & v1.TimeoutFields {
1555
+ Pipeline : & metav1.Duration {Duration : 1 },
1556
+ },
1557
+ },
1558
+ },
1559
+ isCreate : false ,
1560
+ isUpdate : true ,
1561
+ expectedError : apis.FieldError {},
1562
+ }, {
1563
+ name : "is update ctx, baseline is unknown, status changes from Empty to Cancelled" ,
1564
+ baselinePipelineRun : & v1.PipelineRun {
1565
+ Spec : v1.PipelineRunSpec {
1566
+ Status : "" ,
1567
+ },
1568
+ Status : v1.PipelineRunStatus {
1569
+ Status : duckv1.Status {
1570
+ Conditions : duckv1.Conditions {
1571
+ {Type : apis .ConditionSucceeded , Status : corev1 .ConditionUnknown },
1572
+ },
1573
+ },
1574
+ },
1575
+ },
1576
+ pipelineRun : & v1.PipelineRun {
1577
+ Spec : v1.PipelineRunSpec {
1578
+ Status : "Cancelled" ,
1579
+ },
1580
+ },
1581
+ isCreate : false ,
1582
+ isUpdate : true ,
1583
+ expectedError : apis.FieldError {},
1584
+ }, {
1585
+ name : "is update ctx, baseline is unknown, timeouts changes" ,
1586
+ baselinePipelineRun : & v1.PipelineRun {
1587
+ Spec : v1.PipelineRunSpec {
1588
+ Status : "" ,
1589
+ Timeouts : & v1.TimeoutFields {
1590
+ Pipeline : & metav1.Duration {Duration : 0 },
1591
+ },
1592
+ },
1593
+ Status : v1.PipelineRunStatus {
1594
+ Status : duckv1.Status {
1595
+ Conditions : duckv1.Conditions {
1596
+ {Type : apis .ConditionSucceeded , Status : corev1 .ConditionUnknown },
1597
+ },
1598
+ },
1599
+ },
1600
+ },
1601
+ pipelineRun : & v1.PipelineRun {
1602
+ Spec : v1.PipelineRunSpec {
1603
+ Timeouts : & v1.TimeoutFields {
1604
+ Pipeline : & metav1.Duration {Duration : 1 },
1605
+ },
1606
+ },
1607
+ },
1608
+ isCreate : false ,
1609
+ isUpdate : true ,
1610
+ expectedError : apis.FieldError {
1611
+ Message : `invalid value: Once the PipelineRun has started, only status updates are allowed` ,
1612
+ Paths : []string {"" },
1613
+ },
1614
+ }, {
1615
+ name : "is update ctx, baseline is unknown, status changes from PipelineRunPending to Empty, and timeouts changes" ,
1616
+ baselinePipelineRun : & v1.PipelineRun {
1617
+ Spec : v1.PipelineRunSpec {
1618
+ Status : "PipelineRunPending" ,
1619
+ Timeouts : & v1.TimeoutFields {
1620
+ Pipeline : & metav1.Duration {Duration : 0 },
1621
+ },
1622
+ },
1623
+ Status : v1.PipelineRunStatus {
1624
+ Status : duckv1.Status {
1625
+ Conditions : duckv1.Conditions {
1626
+ {Type : apis .ConditionSucceeded , Status : corev1 .ConditionUnknown },
1627
+ },
1628
+ },
1629
+ },
1630
+ },
1631
+ pipelineRun : & v1.PipelineRun {
1632
+ Spec : v1.PipelineRunSpec {
1633
+ Status : "" ,
1634
+ Timeouts : & v1.TimeoutFields {
1635
+ Pipeline : & metav1.Duration {Duration : 1 },
1636
+ },
1637
+ },
1638
+ },
1639
+ isCreate : false ,
1640
+ isUpdate : true ,
1641
+ expectedError : apis.FieldError {
1642
+ Message : `invalid value: Once the PipelineRun has started, only status updates are allowed` ,
1643
+ Paths : []string {"" },
1644
+ },
1645
+ }, {
1646
+ name : "is update ctx, baseline is done, status changes" ,
1647
+ baselinePipelineRun : & v1.PipelineRun {
1648
+ Spec : v1.PipelineRunSpec {
1649
+ Status : "PipelineRunPending" ,
1650
+ },
1651
+ Status : v1.PipelineRunStatus {
1652
+ Status : duckv1.Status {
1653
+ Conditions : duckv1.Conditions {
1654
+ {Type : apis .ConditionSucceeded , Status : corev1 .ConditionTrue },
1655
+ },
1656
+ },
1657
+ },
1658
+ },
1659
+ pipelineRun : & v1.PipelineRun {
1660
+ Spec : v1.PipelineRunSpec {
1661
+ Status : "TaskRunCancelled" ,
1662
+ },
1663
+ },
1664
+ isCreate : false ,
1665
+ isUpdate : true ,
1666
+ expectedError : apis.FieldError {
1667
+ Message : `invalid value: Once the PipelineRun is complete, no updates are allowed` ,
1668
+ Paths : []string {"" },
1669
+ },
1670
+ },
1671
+ }
1672
+
1673
+ for _ , tt := range tests {
1674
+ t .Run (tt .name , func (t * testing.T ) {
1675
+ ctx := config .ToContext (context .Background (), & config.Config {
1676
+ FeatureFlags : & config.FeatureFlags {},
1677
+ Defaults : & config.Defaults {},
1678
+ })
1679
+ if tt .isCreate {
1680
+ ctx = apis .WithinCreate (ctx )
1681
+ }
1682
+ if tt .isUpdate {
1683
+ ctx = apis .WithinUpdate (ctx , tt .baselinePipelineRun )
1684
+ }
1685
+ pr := tt .pipelineRun
1686
+ err := pr .Spec .ValidateUpdate (ctx )
1687
+ if d := cmp .Diff (tt .expectedError .Error (), err .Error (), cmpopts .IgnoreUnexported (apis.FieldError {})); d != "" {
1688
+ t .Errorf ("PipelineRunSpec.ValidateUpdate() errors diff %s" , diff .PrintWantGot (d ))
1689
+ }
1690
+ })
1691
+ }
1692
+ }
0 commit comments