如何转换对象的结构

how to transform the structure of a object

我在terraform中有一个复杂的对象,结构如下 我需要做的是将这个结构转换为另一个结构(我已经发布了所需的结构)然后在 terraform

中使用 foreach 创建资源
StorageSettings{
    storage{
        fileshare{
            directories{}
        }
    }
}

实际代码在这里


locals {

  StorageSettings = {

    CoreBackup = {

      fileshare = {

        shareA = {
          name                 = "myshare"
          storage_account_name = "sa1corebackup"
          quota                = 100

          directories = {

            dirA = {
              name                 = "app"
              share_name           = "myshare"
              storage_account_name = "sa1corebackup"


            }
          }
        }
        shareB = {
          name                 = "myshare2"
          storage_account_name = "sa1corebackup"
          quota                = 150
        }
      }
    }

    MGMTackup = {

      fileshare = {
        ShareA = {
          name                 = "myshare"
          storage_account_name = "mgmtbackup"
          quota                = 200
          enabled_protocol     = "SMB"
          acl = {
            id = "MTIzNDU2Nzg5MDEyMzQ1Njc4OTAxMjM0NTY3ODkwMTI"

            access_policy = {
              permissions = "rwdl"
              start       = "2019-07-02T09:38:21.0000000Z"
              expiry      = "2019-07-02T10:38:21.0000000Z"
            }
          }

          directories = {

            dirA = {

              name                 = "app"
              share_name           = "myshare"
              storage_account_name = "mgmtbackup"

            }

            dirB = {
              name                 = "backup"
              share_name           = "myshare"
              storage_account_name = "mgmtbackup"
            }

          }

        }

        ShareB = {
          name                 = "myshare2"
          storage_account_name = "mgmtbackup"
          quota                = 100
          enabled_protocol     = "SMB"

          acl = {
            id = "MTIzNDU2Nzg5MDEyMzQ1Njc4OTAxMjM0NTY3ODkwMTI"

            access_policy = {
              permissions = "rwdl"
              start       = "2019-07-02T09:38:21.0000000Z"
              expiry      = "2019-07-02T10:38:21.0000000Z"
            }
          }

          directories = {

            dirA = {
              name                 = "app"
              share_name           = "myshare"
              storage_account_name = "mgmtbackup"


            }

            dirB = {
              name                 = "backup"
              share_name           = "myshare"
              storage_account_name = "mgmtbackup"
            }
          }
        }
      }
    }
  }
}




我的问题是如何将结构转换为下面的结构?

storage+fileshare{
    directories{
    }
}

我尝试了下面的代码

  filesharesettings = { for p, v in local.StorageSettings : p => v.fileshare if try(v.fileshare, null) != null }

  directorysettings = {
    for Storage, FileShareSettings in local.filesharesettings : Storage =>
    { for FileShare, FileShareSetting in FileShareSettings : "${Storage} ${FileShare}" => FileShareSetting.directories if lookup(FileShareSetting, "directories", "") != "" }
  }

却只能得到这样的结果

storage{
  storage+fileshare{
    directories{
    }
  }
}

当前输出如下, 请注意这不是我期望的输出,我试图用一些代码(已经发布)转换结构,下面是输出,我期望的输出结构是这个

storage+fileshare{
    directories{
    }
}
Changes to Outputs:
  + dd = {
      + CoreBackup = {
          + CoreBackup shareA = {
              + dirA = {
                  + name                 = "app"
                  + share_name           = "myshare"
                  + storage_account_name = "sa1corebackup"
                }
            }
        }
      + MGMTackup  = {
          + MGMTackup ShareA = {
              + dirA = {
                  + name                 = "app"
                  + share_name           = "myshare"
                  + storage_account_name = "mgmtbackup"
                }
              + dirB = {
                  + name                 = "backup"
                  + share_name           = "myshare"
                  + storage_account_name = "mgmtbackup"
                }
            }
          + MGMTackup ShareB = {
              + dirA = {
                  + name                 = "app"
                  + share_name           = "myshare"
                  + storage_account_name = "mgmtbackup"
                }
              + dirB = {
                  + name                 = "backup"
                  + share_name           = "myshare"
                  + storage_account_name = "mgmtbackup"
                }
            }
        }
    }


谁能帮我解决这个问题?

您的数据源相当复杂,但我认为您可以使用三个 for 循环来做到这一点:

  directorysettings = merge(
        flatten([for storage_name, fileshares in local.StorageSettings:
           {for share_name, share in fileshares["fileshare"]:
               "${storage_name}+${share_name}" => {
                 for directory_name, directory in share["directories"]:
                   directory_name => directory
               } if lookup(share, "directories", "") != ""
           }
        ])...) 

这给出 directorysettings:

{
  "CoreBackup+shareA" = {
    "dirA" = {
      "name" = "app"
      "share_name" = "myshare"
      "storage_account_name" = "sa1corebackup"
    }
  }
  "MGMTackup+ShareA" = {
    "dirA" = {
      "name" = "app"
      "share_name" = "myshare"
      "storage_account_name" = "mgmtbackup"
    }
    "dirB" = {
      "name" = "backup"
      "share_name" = "myshare"
      "storage_account_name" = "mgmtbackup"
    }
  }
  "MGMTackup+ShareB" = {
    "dirA" = {
      "name" = "app"
      "share_name" = "myshare"
      "storage_account_name" = "mgmtbackup"
    }
    "dirB" = {
      "name" = "backup"
      "share_name" = "myshare"
      "storage_account_name" = "mgmtbackup"
    }
  }
}