aboutsummaryrefslogtreecommitdiffstats
path: root/overcloud.yaml
blob: b88d1dcdc94084884cee89e298ca61f2c730a096 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
@media only all and (prefers-color-scheme: dark) {
.highlight .hll { background-color: #49483e }
.highlight .c { color: #75715e } /* Comment */
.highlight .err { color: #960050; background-color: #1e0010 } /* Error */
.highlight .k { color: #66d9ef } /* Keyword */
.highlight .l { color: #ae81ff } /* Literal */
.highlight .n { color: #f8f8f2 } /* Name */
.highlight .o { color: #f92672 } /* Operator */
.highlight .p { color: #f8f8f2 } /* Punctuation */
.highlight .ch { color: #75715e } /* Comment.Hashbang */
.highlight .cm { color: #75715e } /* Comment.Multiline */
.highlight .cp { color: #75715e } /* Comment.Preproc */
.highlight .cpf { color: #75715e } /* Comment.PreprocFile */
.highlight .c1 { color: #75715e } /* Comment.Single */
.highlight .cs { color: #75715e } /* Comment.Special */
.highlight .gd { color: #f92672 } /* Generic.Deleted */
.highlight .ge { font-style: italic } /* Generic.Emph */
.highlight .gi { color: #a6e22e } /* Generic.Inserted */
.highlight .gs { font-weight: bold } /* Generic.Strong */
.highlight .gu { color: #75715e } /* Generic.Subheading */
.highlight .kc { color: #66d9ef } /* Keyword.Constant */
.highlight .kd { color: #66d9ef } /* Keyword.Declaration */
.highlight .kn { color: #f92672 } /* Keyword.Namespace */
.highlight .kp { color: #66d9ef } /* Keyword.Pseudo */
.highlight .kr { color: #66d9ef } /* Keyword.Reserved */
.highlight .kt { color: #66d9ef } /* Keyword.Type */
.highlight .ld { color: #e6db74 } /* Literal.Date */
.highlight .m { color: #ae81ff } /* Literal.Number */
.highlight .s { color: #e6db74 } /* Literal.String */
.highlight .na { color: #a6e22e } /* Name.Attribute */
.highlight .nb { color: #f8f8f2 } /* Name.Builtin */
.highlight .nc { color: #a6e22e } /* Name.Class */
.highlight .no { color: #66d9ef } /* Name.Constant */
.highlight .nd { color: #a6e22e } /* Name.Decorator */
.highlight .ni { color: #f8f8f2 } /* Name.Entity */
.highlight .ne { color: #a6e22e } /* Name.Exception */
.highlight .nf { color: #a6e22e } /* Name.Function */
.highlight .nl { color: #f8f8f2 } /* Name.Label */
.highlight .nn { color: #f8f8f2 } /* Name.Namespace */
.highlight .nx { color: #a6e22e } /* Name.Other */
.highlight .py { color: #f8f8f2 } /* Name.Property */
.highlight .nt { color: #f92672 } /* Name.Tag */
.highlight .nv { color: #f8f8f2 } /* Name.Variable */
.highlight .ow { color: #f92672 } /* Operator.Word */
.highlight .w { color: #f8f8f2 } /* Text.Whitespace */
.highlight .mb { color: #ae81ff } /* Literal.Number.Bin */
.highlight .mf { color: #ae81ff } /* Literal.Number.Float */
.highlight .mh { color: #ae81ff } /* Literal.Number.Hex */
.highlight .mi { color: #ae81ff } /* Literal.Number.Integer */
.highlight .mo { color: #ae81ff } /* Literal.Number.Oct */
.highlight .sa { color: #e6db74 } /* Literal.String.Affix */
.highlight .sb { color: #e6db74 } /* Literal.String.Backtick */
.highlight .sc { color: #e6db74 } /* Literal.String.Char */
.highlight .dl { color: #e6db74 } /* Literal.String.Delimiter */
.highlight .sd { color: #e6db74 } /* Literal.String.Doc */
.highlight .s2 { color: #e6db74 } /* Literal.String.Double */
.highlight .se { color: #ae81ff } /* Literal.String.Escape */
.highlight .sh { color: #e6db74 } /* Literal.String.Heredoc */
.highlight .si { color: #e6db74 } /* Literal.String.Interpol */
.highlight .sx { color: #e6db74 } /* Literal.String.Other */
.highlight .sr { color: #e6db74 } /* Literal.String.Regex */
.highlight .s1 { color: #e6db74 } /* Literal.String.Single */
.highlight .ss { color: #e6db74 } /* Literal.String.Symbol */
.highlight .bp { color: #f8f8f2 } /* Name.Builtin.Pseudo */
.highlight .fm { color: #a6e22e } /* Name.Function.Magic */
.highlight .vc { color: #f8f8f2 } /* Name.Variable.Class */
.highlight .vg { color: #f8f8f2 } /* Name.Variable.Global */
.highlight .vi { color: #f8f8f2 } /* Name.Variable.Instance */
.highlight .vm { color: #f8f8f2 } /* Name.Variable.Magic */
.highlight .il { color: #ae81ff } /* Literal.Number.Integer.Long */
}
@media (prefers-color-scheme: light) {
.highlight .hll { background-color: #ffffcc }
.highlight .c { color: #888888 } /* Comment */
.highlight .err { color: #a61717; background-color: #e3d2d2 } /* Error */
.highlight .k { color: #008800; font-weight: bold } /* Keyword */
.highlight .ch { color: #888888 } /* Comment.Hashbang */
.highlight .cm { color: #888888 } /* Comment.Multiline */
.highlight .cp { color: #cc0000; font-weight: bold } /* Comment.Preproc */
.highlight .cpf { color: #888888 } /* Comment.PreprocFile */
.highlight .c1 { color: #888888 } /* Comment.Single */
.highlight .cs { color: #cc0000; font-weight: bold; background-color: #fff0f0 } /* Comment.Special */
.highlight .gd { color: #000000; background-color: #ffdddd } /* Generic.Deleted */
.highlight .ge { font-style: italic } /* Generic.Emph */
.highlight .gr { color: #aa0000 } /* Generic.Error */
.highlight .gh { color: #333333 } /* Generic.Heading */
.highlight .gi { color: #000000; background-color: #ddffdd } /* Generic.Inserted */
.highlight .go { color: #888888 } /* Generic.Output */
.highlight .gp { color: #555555 } /* Generic.Prompt */
.highlight .gs { font-weight: bold } /* Generic.Strong */
.highlight .gu { color: #666666 } /* Generic.Subheading */
.highlight .gt { color: #aa0000 } /* Generic.Traceback */
.highlight .kc { color: #008800; font-weight: bold } /* Keyword.Constant */
.highlight .kd { color: #008800; font-weight: bold } /* Keyword.Declaration */
.highlight .kn { color: #008800; font-weight: bold } /* Keyword.Namespace */
.highlight .kp { color: #008800 } /* Keyword.Pseudo */
.highlight .kr { color: #008800; font-weight: bold } /* Keyword.Reserved */
.highlight .kt { color: #888888; font-weight: bold } /* Keyword.Type */
.highlight .m { color: #0000DD; font-weight: bold } /* Literal.Number */
.highlight .s { color: #dd2200; background-color: #fff0f0 } /* Literal.String */
.highlight .na { color: #336699 } /* Name.Attribute */
.highlight .nb { color: #003388 } /* Name.Builtin */
.highlight .nc { color: #bb0066; font-weight: bold } /* Name.Class */
.highlight .no { color: #003366; font-weight: bold } /* Name.Constant */
.highlight .nd { color: #555555 } /* Name.Decorator */
.highlight .ne { color: #bb0066; font-weight: bold } /* Name.Exception */
.highlight .nf { color: #0066bb; font-weight: bold } /* Name.Function */
.highlight .nl { color: #336699; font-style: italic } /* Name.Label */
.highlight .nn { color: #bb0066; font-weight: bold } /* Name.Namespace */
.highlight .py { color: #336699; font-weight: bold } /* Name.Property */
.highlight .nt { color: #bb0066; font-weight: bold } /* Name.Tag */
.highlight .nv { color: #336699 } /* Name.Variable */
.highlight .ow { color: #008800 } /* Operator.Word */
.highlight .w { color: #bbbbbb } /* Text.Whitespace */
.highlight .mb { color: #0000DD; font-weight: bold } /* Literal.Number.Bin */
.highlight .mf { color: #0000DD; font-weight: bold } /* Literal.Number.Float */
.highlight .mh { color: #0000DD; font-weight: bold } /* Literal.Number.Hex */
.highlight .mi { color: #0000DD; font-weight: bold } /* Literal.Number.Integer */
.highlight .mo { color: #0000DD; font-weight: bold } /* Literal.Number.Oct */
.highlight .sa { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Affix */
.highlight .sb { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Backtick */
.highlight .sc { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Char */
.highlight .dl { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Delimiter */
.highlight .sd { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Doc */
.highlight .s2 { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Double */
.highlight .se { color: #0044dd; background-color: #fff0f0 } /* Literal.String.Escape */
.highlight .sh { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Heredoc */
.highlight .si { color: #3333bb; background-color: #fff0f0 } /* Literal.String.Interpol */
.highlight .sx { color: #22bb22; background-color: #f0fff0 } /* Literal.String.Other */
.highlight .sr { color: #008800; background-color: #fff0ff } /* Literal.String.Regex */
.highlight .s1 { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Single */
.highlight .ss { color: #aa6600; background-color: #fff0f0 } /* Literal.String.Symbol */
.highlight .bp { color: #003388 } /* Name.Builtin.Pseudo */
.highlight .fm { color: #0066bb; font-weight: bold } /* Name.Function.Magic */
.highlight .vc { color: #336699 } /* Name.Variable.Class */
.highlight .vg { color: #dd7700 } /* Name.Variable.Global */
.highlight .vi { color: #3333bb } /* Name.Variable.Instance */
.highlight .vm { color: #336699 } /* Name.Variable.Magic */
.highlight .il { color: #0000DD; font-weight: bold } /* Literal.Number.Integer.Long */
}
resource_registry:

  # This initiates the upgrades for ceilometer api to run under apache wsgi
  OS::TripleO::Tasks::UpdateWorkflow: ../extraconfig/tasks/major_upgrade_ceilometer_wsgi_mitaka_newton.yaml

  # no-op the rest
  OS::TripleO::PostDeploySteps: OS::Heat::None
#n353'>353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 368 369 370 371 372 373 374 375 376 377 378 379 380 381 382 383 384 385 386 387 388 389 390 391 392 393 394 395 396 397 398 399 400 401 402 403 404 405 406 407 408 409 410 411 412 413 414 415 416 417 418 419 420 421 422 423 424 425 426 427 428 429 430 431 432 433 434 435 436 437 438 439 440 441 442 443 444 445 446 447 448 449 450 451 452 453 454 455 456 457 458 459 460 461 462 463 464 465 466 467 468 469 470 471 472 473 474 475 476 477 478 479 480 481 482 483 484 485 486 487 488 489 490 491 492 493 494 495 496 497 498 499 500 501 502 503 504 505 506 507 508 509 510 511 512 513 514 515 516 517 518 519 520 521 522 523 524 525 526 527 528 529 530 531 532 533 534 535 536 537 538 539 540 541 542 543 544 545 546 547 548 549 550 551 552 553 554 555 556 557 558 559 560 561 562 563 564 565 566 567 568 569 570 571 572 573 574 575 576 577 578 579 580 581 582 583 584 585 586 587 588 589 590 591 592 593 594 595 596 597 598 599 600 601 602 603 604 605 606 607 608 609 610 611 612 613 614 615 616 617 618 619 620 621 622 623 624 625 626 627 628 629 630 631 632 633 634 635 636 637 638 639 640 641 642 643 644 645 646 647 648 649 650 651 652 653 654 655 656 657 658 659 660 661 662 663 664 665 666 667 668 669 670 671 672 673 674 675 676 677 678 679 680 681 682 683 684 685 686 687 688 689 690 691 692 693 694 695 696 697 698 699 700 701 702 703 704 705 706 707 708 709 710 711 712 713 714 715 716 717 718 719 720 721 722 723 724 725 726 727 728 729 730 731 732 733 734 735 736 737 738 739 740 741 742 743 744 745 746 747 748 749 750 751 752 753 754 755 756 757 758 759 760 761 762 763 764 765 766 767 768 769 770 771 772 773 774 775 776 777 778 779 780 781 782 783 784 785 786 787 788 789 790 791 792 793 794 795 796 797 798 799 800 801 802 803 804 805 806 807 808 809 810 811 812 813 814 815 816 817 818 819 820 821 822 823 824 825 826 827 828 829 830 831 832 833 834 835 836 837 838 839 840 841 842 843 844 845 846 847 848 849 850 851 852 853 854 855 856 857 858 859 860 861 862 863 864 865 866 867 868 869 870 871 872 873 874 875 876 877 878 879 880 881 882 883 884 885 886 887 888 889 890 891 892 893 894 895 896 897 898 899 900 901 902 903 904 905 906 907 908 909 910 911 912 913 914 915 916 917 918 919 920 921 922 923 924 925 926 927 928 929 930 931 932 933 934 935 936 937 938 939 940 941 942 943 944 945 946 947 948 949 950 951 952 953 954 955 956 957 958 959 960 961 962 963 964 965 966 967 968 969 970 971 972 973 974 975 976 977 978 979 980 981 982 983 984 985 986 987 988 989 990 991 992 993 994
heat_template_version: 2016-04-08

description: >
  Deploy an OpenStack environment, consisting of several node types (roles),
  Controller, Compute, BlockStorage, SwiftStorage and CephStorage.  The Storage
  roles enable independent scaling of the storage components, but the minimal
  deployment is one Controller and one Compute node.


# TODO(shadower): we should probably use the parameter groups to put
# some order in here.
parameters:

  # Common parameters (not specific to a role)
  CloudName:
    default: overcloud
    description: The DNS name of this cloud. E.g. ci-overcloud.tripleo.org
    type: string
  ControlFixedIPs:
    default: []
    description: Should be used for arbitrary ips.
    type: json
  InternalApiVirtualFixedIPs:
    default: []
    description: >
        Control the IP allocation for the InternalApiVirtualInterface port. E.g.
        [{'ip_address':'1.2.3.4'}]
    type: json
  NeutronControlPlaneID:
    default: 'ctlplane'
    type: string
    description: Neutron ID or name for ctlplane network.
  NeutronPublicInterface:
    default: nic1
    description: What interface to bridge onto br-ex for network nodes.
    type: string
  PublicVirtualFixedIPs:
    default: []
    description: >
        Control the IP allocation for the PublicVirtualInterface port. E.g.
        [{'ip_address':'1.2.3.4'}]
    type: json
  RabbitCookieSalt:
    type: string
    default: unset
    description: Salt for the rabbit cookie, change this to force the randomly generated rabbit cookie to change.
  StorageVirtualFixedIPs:
    default: []
    description: >
        Control the IP allocation for the StorageVirtualInterface port. E.g.
        [{'ip_address':'1.2.3.4'}]
    type: json
  StorageMgmtVirtualFixedIPs:
    default: []
    description: >
        Control the IP allocation for the StorageMgmgVirtualInterface port. E.g.
        [{'ip_address':'1.2.3.4'}]
    type: json
  CloudDomain:
    default: 'localdomain'
    type: string
    description: >
      The DNS domain used for the hosts. This should match the dhcp_domain
      configured in the Undercloud neutron. Defaults to localdomain.
  ServerMetadata:
    default: {}
    description: >
      Extra properties or metadata passed to Nova for the created nodes in
      the overcloud. It's accessible via the Nova metadata API.
    type: json

  # Controller-specific params
  ControllerCount:
    type: number
    default: 1
  controllerExtraConfig:
    default: {}
    description: |
      Deprecated. Use ControllerExtraConfig via parameter_defaults instead.
    type: json
  ExtraConfig:
    default: {}
    description: |
      Additional configuration to inject into the cluster. The format required
      may be implementation specific, e.g puppet hieradata.  Any role specific
      ExtraConfig, e.g controllerExtraConfig takes precedence over ExtraConfig.
    type: json
  SwiftHashSuffix:
    description: A random string to be used as a salt when hashing to determine mappings in the ring.
    type: string
    hidden: true


# Compute-specific params
  ComputeCount:
    type: number
    default: 1
  HypervisorNeutronPhysicalBridge:
    default: 'br-ex'
    description: >
      An OVS bridge to create on each hypervisor. This defaults to br-ex the
      same as the control plane nodes, as we have a uniform configuration of
      the openvswitch agent. Typically should not need to be changed.
    type: string
  HypervisorNeutronPublicInterface:
    default: nic1
    description: What interface to add to the HypervisorNeutronPhysicalBridge.
    type: string

  ControllerServices:
    default:
      - OS::TripleO::Services::CephMon
      - OS::TripleO::Services::CephExternal
      - OS::TripleO::Services::CinderApi
      - OS::TripleO::Services::CinderBackup
      - OS::TripleO::Services::CinderScheduler
      - OS::TripleO::Services::CinderVolume
      - OS::TripleO::Services::Core
      - OS::TripleO::Services::Kernel
      - OS::TripleO::Services::Keystone
      - OS::TripleO::Services::GlanceApi
      - OS::TripleO::Services::GlanceRegistry
      - OS::TripleO::Services::HeatApi
      - OS::TripleO::Services::HeatApiCfn
      - OS::TripleO::Services::HeatApiCloudwatch
      - OS::TripleO::Services::HeatEngine
      - OS::TripleO::Services::MySQL
      - OS::TripleO::Services::NeutronDhcpAgent
      - OS::TripleO::Services::NeutronL3Agent
      - OS::TripleO::Services::NeutronMetadataAgent
      - OS::TripleO::Services::NeutronApi
      - OS::TripleO::Services::NeutronCorePlugin
      - OS::TripleO::Services::NeutronOvsAgent
      - OS::TripleO::Services::RabbitMQ
      - OS::TripleO::Services::HAproxy
      - OS::TripleO::Services::Keepalived
      - OS::TripleO::Services::Memcached
      - OS::TripleO::Services::Pacemaker
      - OS::TripleO::Services::Redis
      - OS::TripleO::Services::NovaConductor
      - OS::TripleO::Services::MongoDb
      - OS::TripleO::Services::NovaApi
      - OS::TripleO::Services::NovaScheduler
      - OS::TripleO::Services::NovaConsoleauth
      - OS::TripleO::Services::NovaVncproxy
      - OS::TripleO::Services::Ntp
      - OS::TripleO::Services::SwiftProxy
      - OS::TripleO::Services::SwiftStorage
      - OS::TripleO::Services::SwiftRingBuilder
      - OS::TripleO::Services::Snmp
      - OS::TripleO::Services::Timezone
      - OS::TripleO::Services::CeilometerApi
      - OS::TripleO::Services::CeilometerCollector
      - OS::TripleO::Services::CeilometerExpirer
      - OS::TripleO::Services::CeilometerAgentCentral
      - OS::TripleO::Services::CeilometerAgentNotification
      - OS::TripleO::Services::Horizon
      - OS::TripleO::Services::GnocchiApi
      - OS::TripleO::Services::GnocchiMetricd
      - OS::TripleO::Services::GnocchiStatsd
      - OS::Tripleo::Services::ManilaApi
      - OS::Tripleo::Services::ManilaScheduler
      - OS::Tripleo::Services::ManilaShare
      - OS::TripleO::Services::AodhApi
      - OS::TripleO::Services::AodhEvaluator
      - OS::TripleO::Services::AodhNotifier
      - OS::TripleO::Services::AodhListener
      - OS::TripleO::Services::SaharaApi
      - OS::TripleO::Services::SaharaEngine
      - OS::TripleO::Services::IronicApi
      - OS::TripleO::Services::IronicConductor
      - OS::TripleO::Services::NovaIronic
      - OS::TripleO::Services::TripleoPackages
      - OS::TripleO::Services::TripleoFirewall
    description: A list of service resources (configured in the Heat
                 resource_registry) which represent nested stacks
                 for each service that should get installed on the Controllers.
    type: comma_delimited_list

  ComputeServices:
    default:
      - OS::TripleO::Services::CephClient
      - OS::TripleO::Services::CephExternal
      - OS::TripleO::Services::Timezone
      - OS::TripleO::Services::Ntp
      - OS::TripleO::Services::Snmp
      - OS::TripleO::Services::NovaCompute
      - OS::TripleO::Services::NovaLibvirt
      - OS::TripleO::Services::Kernel
      - OS::TripleO::Services::ComputeNeutronCorePlugin
      - OS::TripleO::Services::ComputeNeutronOvsAgent
      - OS::TripleO::Services::ComputeCeilometerAgent
      - OS::TripleO::Services::ComputeNeutronL3Agent
      - OS::TripleO::Services::ComputeNeutronMetadataAgent
      - OS::TripleO::Services::TripleoPackages
      - OS::TripleO::Services::TripleoFirewall
    description: A list of service resources (configured in the Heat
                 resource_registry) which represent nested stacks
                 for each service that should get installed on the Compute Nodes.
    type: comma_delimited_list

# Block storage specific parameters
  BlockStorageCount:
    type: number
    default: 0
  BlockStorageExtraConfig:
    default: {}
    description: |
      BlockStorage specific configuration to inject into the cluster. Same
      structure as ExtraConfig.
    type: json
  BlockStorageServices:
    default:
      - OS::TripleO::Services::CinderVolume
      - OS::TripleO::Services::Kernel
      - OS::TripleO::Services::Ntp
      - OS::TripleO::Services::Timezone
      - OS::TripleO::Services::Snmp
      - OS::TripleO::Services::TripleoPackages
      - OS::TripleO::Services::TripleoFirewall
    description: A list of service resources (configured in the Heat
                 resource_registry) which represent nested stacks
                 for each service that should get installed on the BlockStorage nodes.
    type: comma_delimited_list

# Object storage specific parameters
  ObjectStorageCount:
    type: number
    default: 0
  ObjectStorageExtraConfig:
    default: {}
    description: |
      ObjectStorage specific configuration to inject into the cluster. Same
      structure as ExtraConfig.
    type: json
  ObjectStorageServices:
    default:
      - OS::TripleO::Services::Kernel
      - OS::TripleO::Services::Ntp
      - OS::TripleO::Services::SwiftStorage
      - OS::TripleO::Services::SwiftRingBuilder
      - OS::TripleO::Services::Snmp
      - OS::TripleO::Services::Timezone
      - OS::TripleO::Services::TripleoPackages
      - OS::TripleO::Services::TripleoFirewall
    description: A list of service resources (configured in the Heat
                 resource_registry) which represent nested stacks
                 for each service that should get installed on the ObjectStorage nodes.
                 Note this role currently only supports steps 2, 3 and 4 configuration.
    type: comma_delimited_list


# Ceph storage specific parameters
  CephStorageCount:
    type: number
    default: 0
  CephStorageExtraConfig:
    default: {}
    description: |
      CephStorage specific configuration to inject into the cluster. Same
      structure as ExtraConfig.
    type: json
  CephStorageServices:
    default:
      - OS::TripleO::Services::CephOSD
      - OS::TripleO::Services::Kernel
      - OS::TripleO::Services::Ntp
      - OS::TripleO::Services::Timezone
      - OS::TripleO::Services::TripleoPackages
      - OS::TripleO::Services::TripleoFirewall
    description: A list of service resources (configured in the Heat
                 resource_registry) which represent nested stacks
                 for each service that should get installed on the CephStorage nodes.
    type: comma_delimited_list

  # Hostname format for each role
  # Note %index% is translated into the index of the node, e.g 0/1/2 etc
  # and %stackname% is replaced with OS::stack_name in the template below.
  # If you want to use the heat generated names, pass '' (empty string).
  ControllerHostnameFormat:
    type: string
    description: Format for Controller node hostnames
    default: '%stackname%-controller-%index%'
  ComputeHostnameFormat:
    type: string
    description: Format for Compute node hostnames
    default: '%stackname%-novacompute-%index%'
  BlockStorageHostnameFormat:
    type: string
    description: Format for BlockStorage node hostnames
    default: '%stackname%-blockstorage-%index%'
  ObjectStorageHostnameFormat:
    type: string
    description: Format for SwiftStorage node hostnames
    default: '%stackname%-objectstorage-%index%'
  CephStorageHostnameFormat:
    type: string
    description: Format for CephStorage node hostnames
    default: '%stackname%-cephstorage-%index%'

  # Identifiers to trigger tasks on nodes
  UpdateIdentifier:
    default: ''
    type: string
    description: >
      Setting to a previously unused value during stack-update will trigger
      package update on all nodes
  DeployIdentifier:
    default: ''
    type: string
    description: >
      Setting this to a unique value will re-run any deployment tasks which
      perform configuration on a Heat stack-update.

  # If you want to remove a specific node from a resource group, you can pass
  # the node name or id as a <Group>RemovalPolicies parameter, for example:
  # ComputeRemovalPolicies: [{'resource_list': ['0']}]
  ControllerRemovalPolicies:
    default: []
    type: json
    description: >
      List of resources to be removed from ControllerResourceGroup when
      doing an update which requires removal of specific resources.
  ComputeRemovalPolicies:
    default: []
    type: json
    description: >
      List of resources to be removed from ComputeResourceGroup when
      doing an update which requires removal of specific resources.
  BlockStorageRemovalPolicies:
    default: []
    type: json
    description: >
      List of resources to be removed from BlockStorageResourceGroup when
      doing an update which requires removal of specific resources.
  ObjectStorageRemovalPolicies:
    default: []
    type: json
    description: >
      List of resources to be removed from ObjectStorageResourceGroup when
      doing an update which requires removal of specific resources.
  CephStorageRemovalPolicies:
    default: []
    type: json
    description: >
      List of resources to be removed from CephStorageResourceGroup when
      doing an update which requires removal of specific resources.

parameter_groups:
- label: deprecated
  description: Do not use deprecated params, they will be removed.
  parameters:
  - controllerExtraConfig


resources:

  HeatAuthEncryptionKey:
    type: OS::Heat::RandomString

  PcsdPassword:
    type: OS::Heat::RandomString
    properties:
      length: 16

  HorizonSecret:
    type: OS::Heat::RandomString
    properties:
      length: 10

  ServiceNetMap:
    type: OS::TripleO::ServiceNetMap

  EndpointMap:
    type: OS::TripleO::EndpointMap
    properties:
      CloudName: {get_param: CloudName}
      NetIpMap: {get_attr: [VipMap, net_ip_map]}
      ServiceNetMap: {get_attr: [ServiceNetMap, service_net_map]}

  ControllerServiceChain:
    type: OS::TripleO::Services
    properties:
      Services: {get_param: ControllerServices}
      ServiceNetMap: {get_attr: [ServiceNetMap, service_net_map]}
      EndpointMap: {get_attr: [EndpointMap, endpoint_map]}
      DefaultPasswords: {get_attr: [DefaultPasswords, passwords]}

  Controller:
    type: OS::Heat::ResourceGroup
    depends_on: Networks
    properties:
      count: {get_param: ControllerCount}
      removal_policies: {get_param: ControllerRemovalPolicies}
      resource_def:
        type: OS::TripleO::Controller
        properties:
          CloudDomain: {get_param: CloudDomain}
          controllerExtraConfig: {get_param: controllerExtraConfig}
          HeatAuthEncryptionKey: {get_resource: HeatAuthEncryptionKey}
          HorizonSecret: {get_resource: HorizonSecret}
          PcsdPassword: {get_resource: PcsdPassword}
          RedisVirtualIP: {get_attr: [RedisVirtualIP, ip_address]}
          RedisVirtualIPUri: {get_attr: [RedisVirtualIP, ip_address_uri]}
          ServiceNetMap: {get_attr: [ServiceNetMap, service_net_map]}
          EndpointMap: {get_attr: [EndpointMap, endpoint_map]}
          Hostname:
            str_replace:
              template: {get_param: ControllerHostnameFormat}
              params:
                '%stackname%': {get_param: 'OS::stack_name'}
          NodeIndex: '%index%'
          ServiceConfigSettings: {get_attr: [ControllerServiceChain, role_data, config_settings]}
          ServiceNames: {get_attr: [ControllerServiceChain, role_data, service_names]}

  ComputeServiceChain:
    type: OS::TripleO::Services
    properties:
      Services: {get_param: ComputeServices}
      ServiceNetMap: {get_attr: [ServiceNetMap, service_net_map]}
      EndpointMap: {get_attr: [EndpointMap, endpoint_map]}
      DefaultPasswords: {get_attr: [DefaultPasswords, passwords]}

  Compute:
    type: OS::Heat::ResourceGroup
    depends_on: Networks
    properties:
      count: {get_param: ComputeCount}
      removal_policies: {get_param: ComputeRemovalPolicies}
      resource_def:
        type: OS::TripleO::Compute
        properties:
          CloudDomain: {get_param: CloudDomain}
          NeutronPhysicalBridge: {get_param: HypervisorNeutronPhysicalBridge}
          NeutronPublicInterface: {get_param: HypervisorNeutronPublicInterface}
          # L3 HA and Failover is not relevant for Computes, should be removed
          NovaApiHost: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, NovaApiNetwork]}]}
          NovaPublicIP: {get_attr: [VipMap, net_ip_map, external]}
          ServiceNetMap: {get_attr: [ServiceNetMap, service_net_map]}
          EndpointMap: {get_attr: [EndpointMap, endpoint_map]}
          Hostname:
            str_replace:
              template: {get_param: ComputeHostnameFormat}
              params:
                '%stackname%': {get_param: 'OS::stack_name'}
          NodeIndex: '%index%'
          ServiceConfigSettings: {get_attr: [ComputeServiceChain, role_data, config_settings]}
          ServiceNames: {get_attr: [ComputeServiceChain, role_data, service_names]}

  BlockStorageServiceChain:
    type: OS::TripleO::Services
    properties:
      Services: {get_param: BlockStorageServices}
      ServiceNetMap: {get_attr: [ServiceNetMap, service_net_map]}
      EndpointMap: {get_attr: [EndpointMap, endpoint_map]}
      DefaultPasswords: {get_attr: [DefaultPasswords, passwords]}

  BlockStorage:
    type: OS::Heat::ResourceGroup
    depends_on: Networks
    properties:
      count: {get_param: BlockStorageCount}
      removal_policies: {get_param: BlockStorageRemovalPolicies}
      resource_def:
        type: OS::TripleO::BlockStorage
        properties:
          UpdateIdentifier: {get_param: UpdateIdentifier}
          Hostname:
            str_replace:
              template: {get_param: BlockStorageHostnameFormat}
              params:
                '%stackname%': {get_param: 'OS::stack_name'}
          ServiceNetMap: {get_attr: [ServiceNetMap, service_net_map]}
          ExtraConfig: {get_param: ExtraConfig}
          BlockStorageExtraConfig: {get_param: BlockStorageExtraConfig}
          CloudDomain: {get_param: CloudDomain}
          ServerMetadata: {get_param: ServerMetadata}
          NodeIndex: '%index%'
          ServiceConfigSettings: {get_attr: [BlockStorageServiceChain, role_data, config_settings]}
          ServiceNames: {get_attr: [BlockStorageServiceChain, role_data, service_names]}

  ObjectStorageServiceChain:
    type: OS::TripleO::Services
    properties:
      Services: {get_param: ObjectStorageServices}
      ServiceNetMap: {get_attr: [ServiceNetMap, service_net_map]}
      EndpointMap: {get_attr: [EndpointMap, endpoint_map]}
      DefaultPasswords: {get_attr: [DefaultPasswords, passwords]}

  ObjectStorage:
    type: OS::Heat::ResourceGroup
    depends_on: Networks
    properties:
      count: {get_param: ObjectStorageCount}
      removal_policies: {get_param: ObjectStorageRemovalPolicies}
      resource_def:
        type: OS::TripleO::ObjectStorage
        properties:
          HashSuffix: {get_param: SwiftHashSuffix}
          UpdateIdentifier: {get_param: UpdateIdentifier}
          ServiceNetMap: {get_attr: [ServiceNetMap, service_net_map]}
          Hostname:
            str_replace:
              template: {get_param: ObjectStorageHostnameFormat}
              params:
                '%stackname%': {get_param: 'OS::stack_name'}
          ExtraConfig: {get_param: ExtraConfig}
          ObjectStorageExtraConfig: {get_param: ObjectStorageExtraConfig}
          CloudDomain: {get_param: CloudDomain}
          ServerMetadata: {get_param: ServerMetadata}
          NodeIndex: '%index%'
          ServiceConfigSettings: {get_attr: [ObjectStorageServiceChain, role_data, config_settings]}
          ServiceNames: {get_attr: [ObjectStorageServiceChain, role_data, service_names]}

  CephStorageServiceChain:
    type: OS::TripleO::Services
    properties:
      Services: {get_param: CephStorageServices}
      ServiceNetMap: {get_attr: [ServiceNetMap, service_net_map]}
      EndpointMap: {get_attr: [EndpointMap, endpoint_map]}
      DefaultPasswords: {get_attr: [DefaultPasswords, passwords]}

  CephStorage:
    type: OS::Heat::ResourceGroup
    depends_on: Networks
    properties:
      count: {get_param: CephStorageCount}
      removal_policies: {get_param: CephStorageRemovalPolicies}
      resource_def:
        type: OS::TripleO::CephStorage
        properties:
          ServiceNetMap: {get_attr: [ServiceNetMap, service_net_map]}
          UpdateIdentifier: {get_param: UpdateIdentifier}
          Hostname:
            str_replace:
              template: {get_param: CephStorageHostnameFormat}
              params:
                '%stackname%': {get_param: 'OS::stack_name'}
          ExtraConfig: {get_param: ExtraConfig}
          CephStorageExtraConfig: {get_param: CephStorageExtraConfig}
          CloudDomain: {get_param: CloudDomain}
          ServerMetadata: {get_param: ServerMetadata}
          NodeIndex: '%index%'
          ServiceConfigSettings: {get_attr: [CephStorageServiceChain, role_data, config_settings]}
          ServiceNames: {get_attr: [CephStorageServiceChain, role_data, service_names]}

  ControllerIpListMap:
    type: OS::TripleO::Network::Ports::NetIpListMap
    properties:
      ControlPlaneIpList: {get_attr: [Controller, ip_address]}
      ExternalIpList: {get_attr: [Controller, external_ip_address]}
      InternalApiIpList: {get_attr: [Controller, internal_api_ip_address]}
      StorageIpList: {get_attr: [Controller, storage_ip_address]}
      StorageMgmtIpList: {get_attr: [Controller, storage_mgmt_ip_address]}
      TenantIpList: {get_attr: [Controller, tenant_ip_address]}
      ManagementIpList: {get_attr: [Controller, management_ip_address]}

  allNodesConfig:
    type: OS::TripleO::AllNodes::SoftwareConfig
    properties:
      hosts:
        - list_join:
            - '\n'
            - {get_attr: [Compute, hosts_entry]}
        - list_join:
            - '\n'
            - {get_attr: [Controller, hosts_entry]}
        - list_join:
            - '\n'
            - {get_attr: [BlockStorage, hosts_entry]}
        - list_join:
            - '\n'
            - {get_attr: [ObjectStorage, hosts_entry]}
        - list_join:
            - '\n'
            - {get_attr: [CephStorage, hosts_entry]}
      controller_ips: {get_attr: [Controller, ip_address]}
      controller_names: {get_attr: [Controller, hostname]}
      rabbit_node_ips: {get_attr: [ControllerIpListMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, RabbitmqNetwork]}]}
      mongo_node_ips: {get_attr: [ControllerIpListMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, MongodbNetwork]}]}
      redis_node_ips: {get_attr: [ControllerIpListMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, RedisNetwork]}]}
      memcache_node_ips: {get_attr: [ControllerIpListMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, MemcachedNetwork]}]}
      mysql_node_ips: {get_attr: [ControllerIpListMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, MysqlNetwork]}]}
      horizon_node_ips: {get_attr: [ControllerIpListMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, HorizonNetwork]}]}
      heat_api_node_ips: {get_attr: [ControllerIpListMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, HeatApiNetwork]}]}
      swift_proxy_node_ips: {get_attr: [ControllerIpListMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, SwiftProxyNetwork]}]}
      ceilometer_api_node_ips: {get_attr: [ControllerIpListMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, CeilometerApiNetwork]}]}
      aodh_api_node_ips: {get_attr: [ControllerIpListMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, AodhApiNetwork]}]}
      gnocchi_api_node_ips: {get_attr: [ControllerIpListMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, GnocchiApiNetwork]}]}
      nova_api_node_ips: {get_attr: [ControllerIpListMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, NovaApiNetwork]}]}
      nova_metadata_node_ips: {get_attr: [ControllerIpListMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, NovaMetadataNetwork]}]}
      glance_api_node_ips: {get_attr: [ControllerIpListMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, GlanceApiNetwork]}]}
      glance_registry_node_ips: {get_attr: [ControllerIpListMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, GlanceRegistryNetwork]}]}
      cinder_api_node_ips: {get_attr: [ControllerIpListMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, CinderApiNetwork]}]}
      manila_api_node_ips: {get_attr: [ControllerIpListMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, ManilaApiNetwork]}]}
      neutron_api_node_ips: {get_attr: [ControllerIpListMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, NeutronApiNetwork]}]}
      keystone_public_api_node_ips: {get_attr: [ControllerIpListMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, KeystonePublicApiNetwork]}]}
      keystone_admin_api_node_ips: {get_attr: [ControllerIpListMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, KeystoneAdminApiNetwork]}]}
      sahara_api_node_ips: {get_attr: [ControllerIpListMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, SaharaApiNetwork]}]}
      ironic_api_node_ips: {get_attr: [ControllerIpListMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, IronicApiNetwork]}]}
      ceph_mon_node_ips: {get_attr: [ControllerIpListMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, CephPublicNetwork]}]}
      ceph_mon_node_names: {get_attr: [Controller, hostname]}
      DeployIdentifier: {get_param: DeployIdentifier}
      UpdateIdentifier: {get_param: UpdateIdentifier}

  MysqlRootPassword:
    type: OS::Heat::RandomString
    properties:
      length: 10

  RabbitCookie:
    type: OS::Heat::RandomString
    properties:
      length: 20
      salt: {get_param: RabbitCookieSalt}

  DefaultPasswords:
    type: OS::TripleO::DefaultPasswords
    properties:
      DefaultMysqlRootPassword: {get_attr: [MysqlRootPassword, value]}
      DefaultRabbitCookie: {get_attr: [RabbitCookie, value]}
      DefaultHeatAuthEncryptionKey: {get_attr: [HeatAuthEncryptionKey, value]}
      DefaultPcsdPassword: {get_attr: [PcsdPassword, value]}
      DefaultHorizonSecret: {get_attr: [HorizonSecret, value]}

  # creates the network architecture
  Networks:
    type: OS::TripleO::Network

  ControlVirtualIP:
    type: OS::Neutron::Port
    depends_on: Networks
    properties:
      name: control_virtual_ip
      network: {get_param: NeutronControlPlaneID}
      fixed_ips: {get_param: ControlFixedIPs}
      replacement_policy: AUTO

  RedisVirtualIP:
    depends_on: Networks
    type: OS::TripleO::Network::Ports::RedisVipPort
    properties:
      ControlPlaneIP: {get_attr: [ControlVirtualIP, fixed_ips, 0, ip_address]}
      ControlPlaneNetwork: {get_param: NeutronControlPlaneID}
      PortName: redis_virtual_ip
      NetworkName: {get_attr: [ServiceNetMap, service_net_map, RedisNetwork]}
      ServiceName: redis

  # The public VIP is on the External net, falls back to ctlplane
  PublicVirtualIP:
    depends_on: Networks
    type: OS::TripleO::Network::Ports::ExternalVipPort
    properties:
      ControlPlaneIP: {get_attr: [ControlVirtualIP, fixed_ips, 0, ip_address]}
      ControlPlaneNetwork: {get_param: NeutronControlPlaneID}
      PortName: public_virtual_ip
      FixedIPs: {get_param: PublicVirtualFixedIPs}

  InternalApiVirtualIP:
    depends_on: Networks
    type: OS::TripleO::Network::Ports::InternalApiVipPort
    properties:
      ControlPlaneIP: {get_attr: [ControlVirtualIP, fixed_ips, 0, ip_address]}
      PortName: internal_api_virtual_ip
      FixedIPs: {get_param: InternalApiVirtualFixedIPs}

  StorageVirtualIP:
    depends_on: Networks
    type: OS::TripleO::Network::Ports::StorageVipPort
    properties:
      ControlPlaneIP: {get_attr: [ControlVirtualIP, fixed_ips, 0, ip_address]}
      PortName: storage_virtual_ip
      FixedIPs: {get_param: StorageVirtualFixedIPs}

  StorageMgmtVirtualIP:
    depends_on: Networks
    type: OS::TripleO::Network::Ports::StorageMgmtVipPort
    properties:
      ControlPlaneIP: {get_attr: [ControlVirtualIP, fixed_ips, 0, ip_address]}
      PortName: storage_management_virtual_ip
      FixedIPs: {get_param: StorageMgmtVirtualFixedIPs}

  VipMap:
    type: OS::TripleO::Network::Ports::NetVipMap
    properties:
      ControlPlaneIp: {get_attr: [ControlVirtualIP, fixed_ips, 0, ip_address]}
      ExternalIp: {get_attr: [PublicVirtualIP, ip_address]}
      ExternalIpUri: {get_attr: [PublicVirtualIP, ip_address_uri]}
      InternalApiIp: {get_attr: [InternalApiVirtualIP, ip_address]}
      InternalApiIpUri: {get_attr: [InternalApiVirtualIP, ip_address_uri]}
      StorageIp: {get_attr: [StorageVirtualIP, ip_address]}
      StorageIpUri: {get_attr: [StorageVirtualIP, ip_address_uri]}
      StorageMgmtIp: {get_attr: [StorageMgmtVirtualIP, ip_address]}
      StorageMgmtIpUri: {get_attr: [StorageMgmtVirtualIP, ip_address_uri]}
      # No tenant or management VIP required

  VipConfig:
    type: OS::TripleO::VipConfig

  VipDeployment:
    type: OS::Heat::StructuredDeployments
    properties:
      name: VipDeployment
      config: {get_resource: VipConfig}
      servers: {get_attr: [Controller, attributes, nova_server_resource]}
      input_values:
        # service VIP mappings
        keystone_admin_api_vip: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, KeystoneAdminApiNetwork]}]}
        keystone_public_api_vip: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, KeystonePublicApiNetwork]}]}
        neutron_api_vip: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, NeutronApiNetwork]}]}
        cinder_api_vip: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, CinderApiNetwork]}]}
        glance_api_vip: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, GlanceApiNetwork]}]}
        glance_registry_vip: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, GlanceRegistryNetwork]}]}
        swift_proxy_vip: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, SwiftProxyNetwork]}]}
        nova_api_vip: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, NovaApiNetwork]}]}
        nova_metadata_vip: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, NovaMetadataNetwork]}]}
        ceilometer_api_vip: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, CeilometerApiNetwork]}]}
        aodh_api_vip: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, AodhApiNetwork]}]}
        gnocchi_api_vip: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, GnocchiApiNetwork]}]}
        heat_api_vip: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, HeatApiNetwork]}]}
        horizon_vip: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, HorizonNetwork]}]}
        redis_vip: {get_attr: [RedisVirtualIP, ip_address]}
        manila_api_vip: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, ManilaApiNetwork]}]}
        mysql_vip: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, MysqlNetwork]}]}
        rabbit_vip: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, RabbitMqNetwork]}]}
        # direct configuration of Virtual IPs for each network
        control_virtual_ip: {get_attr: [VipMap, net_ip_map, ctlplane]}
        public_virtual_ip: {get_attr: [VipMap, net_ip_map, external]}
        internal_api_virtual_ip: {get_attr: [VipMap, net_ip_map, internal_api]}
        sahara_api_vip: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, SaharaApiNetwork]}]}
        ironic_api_vip: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, IronicApiNetwork]}]}
        storage_virtual_ip: {get_attr: [VipMap, net_ip_map, storage]}
        storage_mgmt_virtual_ip: {get_attr: [VipMap, net_ip_map, storage_mgmt]}

  ControllerSwiftDeployment:
    type: OS::Heat::StructuredDeployments
    properties:
      name: ControllerSwiftDeployment
      config: {get_attr: [SwiftDevicesAndProxyConfig, config_id]}
      servers: {get_attr: [Controller, attributes, nova_server_resource]}

  ObjectStorageSwiftDeployment:
    type: OS::Heat::StructuredDeployments
    properties:
      name: ObjectStorageSwiftDeployment
      config: {get_attr: [SwiftDevicesAndProxyConfig, config_id]}
      servers: {get_attr: [ObjectStorage, attributes, nova_server_resource]}

  SwiftDevicesAndProxyConfig:
    type: OS::TripleO::SwiftDevicesAndProxy::SoftwareConfig
    properties:
      controller_swift_devices: {get_attr: [Controller, swift_device]}
      object_store_swift_devices: {get_attr: [ObjectStorage, swift_device]}
      controller_swift_proxy_memcaches: {get_attr: [Controller, swift_proxy_memcache]}

  ControllerAllNodesDeployment:
    type: OS::Heat::StructuredDeployments
    properties:
      name: ControllerAllNodesDeployment
      config: {get_attr: [allNodesConfig, config_id]}
      servers: {get_attr: [Controller, attributes, nova_server_resource]}
      input_values:
        bootstrap_nodeid: {get_attr: [Controller, resource.0.hostname]}
        bootstrap_nodeid_ip: {get_attr: [Controller, resource.0.ip_address]}

  ComputeAllNodesDeployment:
    type: OS::Heat::StructuredDeployments
    properties:
      name: ComputeAllNodesDeployment
      config: {get_attr: [allNodesConfig, config_id]}
      servers: {get_attr: [Compute, attributes, nova_server_resource]}
      input_values:
        bootstrap_nodeid: {get_attr: [Compute, resource.0.hostname]}
        bootstrap_nodeid_ip: {get_attr: [Compute, resource.0.ip_address]}

  BlockStorageAllNodesDeployment:
    type: OS::Heat::StructuredDeployments
    properties:
      name: BlockStorageAllNodesDeployment
      config: {get_attr: [allNodesConfig, config_id]}
      servers: {get_attr: [BlockStorage, attributes, nova_server_resource]}
      input_values:
        bootstrap_nodeid: {get_attr: [BlockStorage, resource.0.hostname]}
        bootstrap_nodeid_ip: {get_attr: [BlockStorage, resource.0.ip_address]}

  ObjectStorageAllNodesDeployment:
    type: OS::Heat::StructuredDeployments
    properties:
      name: ObjectStorageAllNodesDeployment
      config: {get_attr: [allNodesConfig, config_id]}
      servers: {get_attr: [ObjectStorage, attributes, nova_server_resource]}
      input_values:
        bootstrap_nodeid: {get_attr: [ObjectStorage, resource.0.hostname]}
        bootstrap_nodeid_ip: {get_attr: [ObjectStorage, resource.0.ip_address]}

  CephStorageAllNodesDeployment:
    type: OS::Heat::StructuredDeployments
    properties:
      name: CephStorageAllNodesDeployment
      config: {get_attr: [allNodesConfig, config_id]}
      servers: {get_attr: [CephStorage, attributes, nova_server_resource]}
      input_values:
        bootstrap_nodeid: {get_attr: [CephStorage, resource.0.hostname]}
        bootstrap_nodeid_ip: {get_attr: [CephStorage, resource.0.ip_address]}

  # All Nodes Validations
  AllNodesValidationConfig:
    type: OS::TripleO::AllNodes::Validation
    properties:
      PingTestIps:
        list_join:
        - ' '
        - - {get_attr: [Controller, resource.0.external_ip_address]}
          - {get_attr: [Controller, resource.0.internal_api_ip_address]}
          - {get_attr: [Controller, resource.0.storage_ip_address]}
          - {get_attr: [Controller, resource.0.storage_mgmt_ip_address]}
          - {get_attr: [Controller, resource.0.tenant_ip_address]}
          - {get_attr: [Controller, resource.0.management_ip_address]}

  ControllerAllNodesValidationDeployment:
    type: OS::Heat::StructuredDeployments
    depends_on: ControllerAllNodesDeployment
    properties:
      name: ControllerAllNodesValidationDeployment
      config: {get_resource: AllNodesValidationConfig}
      servers: {get_attr: [Controller, attributes, nova_server_resource]}

  ComputeAllNodesValidationDeployment:
    type: OS::Heat::StructuredDeployments
    depends_on: ComputeAllNodesDeployment
    properties:
      name: ComputeAllNodesValidationDeployment
      config: {get_resource: AllNodesValidationConfig}
      servers: {get_attr: [Compute, attributes, nova_server_resource]}

  BlockStorageAllNodesValidationDeployment:
    type: OS::Heat::StructuredDeployments
    depends_on: BlockStorageAllNodesDeployment
    properties:
      name: BlockStorageAllNodesValidationDeployment
      config: {get_resource: AllNodesValidationConfig}
      servers: {get_attr: [BlockStorage, attributes, nova_server_resource]}

  ObjectStorageAllNodesValidationDeployment:
    type: OS::Heat::StructuredDeployments
    depends_on: ObjectStorageAllNodesDeployment
    properties:
      name: ObjectStorageAllNodesValidationDeployment
      config: {get_resource: AllNodesValidationConfig}
      servers: {get_attr: [ObjectStorage, attributes, nova_server_resource]}

  CephStorageAllNodesValidationDeployment:
    type: OS::Heat::StructuredDeployments
    depends_on: CephStorageAllNodesDeployment
    properties:
      name: CephStorageAllNodesValidationDeployment
      config: {get_resource: AllNodesValidationConfig}
      servers: {get_attr: [CephStorage, attributes, nova_server_resource]}

  UpdateWorkflow:
    type: OS::TripleO::Tasks::UpdateWorkflow
    properties:
      controller_servers: {get_attr: [Controller, attributes, nova_server_resource]}
      compute_servers: {get_attr: [Compute, attributes, nova_server_resource]}
      blockstorage_servers: {get_attr: [BlockStorage, attributes, nova_server_resource]}
      objectstorage_servers: {get_attr: [ObjectStorage, attributes, nova_server_resource]}
      cephstorage_servers: {get_attr: [CephStorage, attributes, nova_server_resource]}
      input_values:
        deploy_identifier: {get_param: DeployIdentifier}
        update_identifier: {get_param: UpdateIdentifier}

  # Optional ExtraConfig for all nodes - all roles are passed in here, but
  # the nested template may configure each role differently (or not at all)
  AllNodesExtraConfig:
    type: OS::TripleO::AllNodesExtraConfig
    depends_on:
      - UpdateWorkflow
      - ComputeAllNodesValidationDeployment
      - BlockStorageAllNodesValidationDeployment
      - ObjectStorageAllNodesValidationDeployment
      - CephStorageAllNodesValidationDeployment
      - ControllerAllNodesValidationDeployment
    properties:
      controller_servers: {get_attr: [Controller, attributes, nova_server_resource]}
      compute_servers: {get_attr: [Compute, attributes, nova_server_resource]}
      blockstorage_servers: {get_attr: [BlockStorage, attributes, nova_server_resource]}
      objectstorage_servers: {get_attr: [ObjectStorage, attributes, nova_server_resource]}
      cephstorage_servers: {get_attr: [CephStorage, attributes, nova_server_resource]}

  # Nested stack deployment runs after all other controller deployments
  ControllerNodesPostDeployment:
    type: OS::TripleO::ControllerPostDeployment
    depends_on: [ControllerAllNodesDeployment, ControllerSwiftDeployment]
    properties:
      servers: {get_attr: [Controller, attributes, nova_server_resource]}
      RoleData: {get_attr: [ControllerServiceChain, role_data]}

  ComputeNodesPostDeployment:
    type: OS::TripleO::ComputePostDeployment
    depends_on: [ComputeAllNodesDeployment]
    properties:
      servers: {get_attr: [Compute, attributes, nova_server_resource]}
      RoleData: {get_attr: [ComputeServiceChain, role_data]}

  ObjectStorageNodesPostDeployment:
    type: OS::TripleO::ObjectStoragePostDeployment
    depends_on: [ObjectStorageSwiftDeployment, ObjectStorageAllNodesDeployment]
    properties:
      servers: {get_attr: [ObjectStorage, attributes, nova_server_resource]}
      RoleData: {get_attr: [ObjectStorageServiceChain, role_data]}

  BlockStorageNodesPostDeployment:
    type: OS::TripleO::BlockStoragePostDeployment
    depends_on: [ControllerNodesPostDeployment, BlockStorageAllNodesDeployment]
    properties:
      servers: {get_attr: [BlockStorage, attributes, nova_server_resource]}
      RoleData: {get_attr: [BlockStorageServiceChain, role_data]}

  CephStorageNodesPostDeployment:
    type: OS::TripleO::CephStoragePostDeployment
    depends_on: [ControllerNodesPostDeployment, CephStorageAllNodesDeployment]
    properties:
      servers: {get_attr: [CephStorage, attributes, nova_server_resource]}
      RoleData: {get_attr: [CephStorageServiceChain, role_data]}

outputs:
  KeystoneURL:
    description: URL for the Overcloud Keystone service
    value: {get_attr: [EndpointMap, endpoint_map, KeystonePublic, uri]}
  KeystoneAdminVip:
    description: Keystone Admin VIP endpoint
    value: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, KeystoneAdminApiNetwork]}]}
  PublicVip:
    description: Controller VIP for public API endpoints
    value: {get_attr: [VipMap, net_ip_map, external]}
  AodhInternalVip:
    description: VIP for Aodh API internal endpoint
    value: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, AodhApiNetwork]}]}
  CeilometerInternalVip:
    description: VIP for Ceilometer API internal endpoint
    value: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, CeilometerApiNetwork]}]}
  CinderInternalVip:
    description: VIP for Cinder API internal endpoint
    value: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, CinderApiNetwork]}]}
  GlanceInternalVip:
    description: VIP for Glance API internal endpoint
    value: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, GlanceApiNetwork]}]}
  GnocchiInternalVip:
    description: VIP for Gnocchi API internal endpoint
    value: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, GnocchiApiNetwork]}]}
  HeatInternalVip:
    description: VIP for Heat API internal endpoint
    value: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, HeatApiNetwork]}]}
  IronicInternalVip:
    description: VIP for Ironic API internal endpoint
    value: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, IronicApiNetwork]}]}
  KeystoneInternalVip:
    description: VIP for Keystone API internal endpoint
    value: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, KeystonePublicApiNetwork]}]}
  ManilaInternalVip:
    description: VIP for Manila API internal endpoint
    value: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, ManilaApiNetwork]}]}
  NeutronInternalVip:
    description: VIP for Neutron API internal endpoint
    value: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, NeutronApiNetwork]}]}
  NovaInternalVip:
    description: VIP for Nova API internal endpoint
    value: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, NovaApiNetwork]}]}
  SaharaInternalVip:
    description: VIP for Sahara API internal endpoint
    value: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, SaharaApiNetwork]}]}
  SwiftInternalVip:
    description: VIP for Swift Proxy internal endpoint
    value: {get_attr: [VipMap, net_ip_map, {get_attr: [ServiceNetMap, service_net_map, SwiftProxyNetwork]}]}
  EndpointMap:
    description: |
      Mapping of the resources with the needed info for their endpoints.
      This includes the protocol used, the IP, port and also a full
      representation of the URI.
    value: {get_attr: [EndpointMap, endpoint_map]}
  HostsEntry:
    description: |
      The content that should be appended to your /etc/hosts if you want to get
      hostname-based access to the deployed nodes (useful for testing without
      setting up a DNS).
    value: {get_attr: [allNodesConfig, hosts_entries]}
  EnabledServices:
    description: The services enabled on each role
    value:
      Controller: {get_attr: [ControllerServiceChain, role_data, service_names]}
      Compute: {get_attr: [ComputeServiceChain, role_data, service_names]}
      BlockStorage: {get_attr: [BlockStorageServiceChain, role_data, service_names]}
      ObjectStorage: {get_attr: [ObjectStorageServiceChain, role_data, service_names]}
      CephStorage: {get_attr: [CephStorageServiceChain, role_data, service_names]}