Repository: hasura/graphql-engine
File: server/src-lib/Hasura/RQL/DDL/Schema/Rename.hs (Haskell)

Code before:
      updateColInArrRel fromQT toQT rnCol <$> decodeValue oldDefV
  liftTx $ updateRel fromQT rn newDefV

updateColInRemoteRelationship
  :: (MonadTx m, CacheRWM m)
  => RemoteRelationshipName -> RenameCol -> m ()
updateColInRemoteRelationship remoteRelationshipName renameCol = do
  let (RenameItem qt oldCol newCol) = renameCol
  (RemoteRelationshipDef remoteSchemaName hasuraFlds remoteFields) <-
    liftTx $ RR.getRemoteRelDefFromCatalog remoteRelationshipName
  let oldColPGTxt = getPGColTxt oldCol
  let newColPGTxt = getPGColTxt newCol
  let oldColFieldName = FieldName $ oldColPGTxt
  let newColFieldName = FieldName $ newColPGTxt
  let modifiedHasuraFlds = Set.insert newColFieldName $ Set.delete oldColFieldName hasuraFlds
  let fieldCalls = unRemoteFields remoteFields
  let oldColName = G.Name $ oldColPGTxt
  let newColName = G.Name $ newColPGTxt
  let modifiedFieldCalls = NE.map (\(FieldCall name args) ->
                                     let remoteArgs = getRemoteArguments args
                                     in FieldCall name $ RemoteArguments $
                                         map (\(G.ObjectFieldG key val) ->
                                                G.ObjectFieldG key $ replaceVariableName oldColName newColName val
                                             ) $ remoteArgs
                                  ) $ fieldCalls
  RR.runUpdateRemoteRelationship (RemoteRelationship remoteRelationshipName qt modifiedHasuraFlds remoteSchemaName (RemoteFields modifiedFieldCalls))
  pure ()
  where
    replaceVariableName :: G.Name -> G.Name -> G.Value -> G.Value
    replaceVariableName oldColName newColName = \case
      G.VVariable (G.Variable oldColName') ->
        G.VVariable $
        if oldColName == oldColName'
        then (G.Variable newColName)
        else (G.Variable oldColName')
      G.VList (G.unListValue -> values) -> G.VList $ G.ListValueG $ map (replaceVariableName oldColName newColName) values
      G.VObject (G.unObjectValue -> values) ->
        G.VObject $ G.ObjectValueG $
        map (\(G.ObjectFieldG key val) -> G.ObjectFieldG key $ replaceVariableName oldColName newColName val) values
      G.VInt i -> G.VInt i
      G.VFloat f -> G.VFloat f
      G.VBoolean b -> G.VBoolean b
      G.VNull -> G.VNull
      G.VString s -> G.VString s
      G.VEnum e -> G.VEnum e

-- rename columns in relationship definitions
updateColInEventTriggerDef
  :: (MonadTx m)
  => TriggerName -> RenameCol -> m ()
updateColInEventTriggerDef trigName rnCol = do

Review comment (performance):
Use `liftTx $ RR.updateRemoteRelInCatalog (RemoteRelationship remoteRelationshipName ... ` to just update the catalog. This also let us to avoid `CacheRWM m` constraint for the function.


Code after:
  oldDefV <- liftTx $ getRelDef fromQT rn
  newDefV <- case riType ri of
    ObjRel -> fmap toJSON $
      updateColInObjRel fromQT toQT rnCol <$> decodeValue oldDefV
    ArrRel -> fmap toJSON $
      updateColInArrRel fromQT toQT rnCol <$> decodeValue oldDefV
  liftTx $ updateRel fromQT rn newDefV

updateColInRemoteRelationship
  :: (MonadTx m)
  => RemoteRelationshipName -> RenameCol -> m ()
updateColInRemoteRelationship remoteRelationshipName renameCol = do
  let (RenameItem qt oldCol newCol) = renameCol
  (RemoteRelationshipDef remoteSchemaName hasuraFlds remoteFields) <-
    liftTx $ RR.getRemoteRelDefFromCatalog remoteRelationshipName qt
  let oldColPGTxt = getPGColTxt oldCol
      newColPGTxt = getPGColTxt newCol
      oldColFieldName = FieldName $ oldColPGTxt
      newColFieldName = FieldName $ newColPGTxt
      modifiedHasuraFlds = Set.insert newColFieldName $ Set.delete oldColFieldName hasuraFlds
      fieldCalls = unRemoteFields remoteFields
      oldColName = G.Name $ oldColPGTxt
      newColName = G.Name $ newColPGTxt
      modifiedFieldCalls = NE.map (\(FieldCall name args) ->
                                     let remoteArgs = getRemoteArguments args
                                     in FieldCall name $ RemoteArguments $
                                         map (\(G.ObjectFieldG key val) ->
                                                G.ObjectFieldG key $ replaceVariableName oldColName newColName val
                                             ) $ remoteArgs
                                  ) $ fieldCalls
  liftTx $ RR.updateRemoteRelInCatalog (RemoteRelationship remoteRelationshipName qt modifiedHasuraFlds remoteSchemaName (RemoteFields modifiedFieldCalls))
  where
    replaceVariableName :: G.Name -> G.Name -> G.Value -> G.Value
    replaceVariableName oldColName newColName = \case
      G.VVariable (G.Variable oldColName') ->
        G.VVariable $
        if oldColName == oldColName'
        then (G.Variable newColName)
        else (G.Variable oldColName')
      G.VList (G.unListValue -> values) -> G.VList $ G.ListValueG $ map (replaceVariableName oldColName newColName) values
      G.VObject (G.unObjectValue -> values) ->
        G.VObject $ G.ObjectValueG $
        map (\(G.ObjectFieldG key val) -> G.ObjectFieldG key $ replaceVariableName oldColName newColName val) values
      G.VInt i -> G.VInt i
      G.VFloat f -> G.VFloat f
      G.VBoolean b -> G.VBoolean b
      G.VNull -> G.VNull
      G.VString s -> G.VString s
      G.VEnum e -> G.VEnum e

-- rename columns in relationship definitions