You can use array_distinct to remove duplicates after collect_set :
from pyspark.sql import functions as F
df1 = df.groupBy("ID", "start date").agg(
F.concat_ws(",", F.collect_set("name")).alias("name"),
F.concat_ws(",", F.collect_set("type")).alias("type"),
).select(
"ID",
"start date",
F.array_join(F.array_distinct(F.split("name", ",")), ",").alias("name"),
F.array_join(F.array_distinct(F.split("type", ",")), ",").alias("type")
)
df1.show()
# +---+----------+-----------------+-------+
# | ID|start date| name| type|
# +---+----------+-----------------+-------+
# | 1|2020/01/01|cheese,fruit,meat|A, C, B|
# +---+----------+-----------------+-------+
Another way using regexp_replace to remove the duplicates:
df1 = df.groupBy("ID", "start date").agg(
F.concat_ws(",", F.collect_set("name")).alias("name"),
F.concat_ws(",", F.collect_set("type")).alias("type"),
).select(
"ID",
"start date",
F.regexp_replace("name", r"\b(\w+)\b\s*,\s*(?=.*\1)", "").alias("name"),
F.regexp_replace("type", r"\b(\w+)\b\s*,\s*(?=.*\1)", "").alias("type")
)