mirror of
				https://github.com/immich-app/immich.git
				synced 2025-11-03 19:29:32 -05:00 
			
		
		
		
	feat(server, web): include pictures of shared albums on map (#7439)
* feat(server, web): include pictures of shared albums on map * run prettier * re-create api clients * implement suggestions from code review * shared from partner -> shared from partners * rename to 'include shared partner assets' * chore: fix tsc error in server and prettier in web * fix: include assets shared via owner albums --------- Co-authored-by: Zack Pollard <zackpollard@ymail.com> Co-authored-by: Jason Rasmussen <jrasm91@gmail.com>
This commit is contained in:
		
							parent
							
								
									d121903b38
								
							
						
					
					
						commit
						48927f5fb9
					
				
							
								
								
									
										6
									
								
								mobile/openapi/doc/AssetApi.md
									
									
									
										generated
									
									
									
								
							
							
						
						
									
										6
									
								
								mobile/openapi/doc/AssetApi.md
									
									
									
										generated
									
									
									
								
							@ -500,7 +500,7 @@ Name | Type | Description  | Notes
 | 
				
			|||||||
[[Back to top]](#) [[Back to API list]](../README.md#documentation-for-api-endpoints) [[Back to Model list]](../README.md#documentation-for-models) [[Back to README]](../README.md)
 | 
					[[Back to top]](#) [[Back to API list]](../README.md#documentation-for-api-endpoints) [[Back to Model list]](../README.md#documentation-for-models) [[Back to README]](../README.md)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
# **getMapMarkers**
 | 
					# **getMapMarkers**
 | 
				
			||||||
> List<MapMarkerResponseDto> getMapMarkers(fileCreatedAfter, fileCreatedBefore, isArchived, isFavorite, withPartners)
 | 
					> List<MapMarkerResponseDto> getMapMarkers(fileCreatedAfter, fileCreatedBefore, isArchived, isFavorite, withPartners, withSharedAlbums)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@ -528,9 +528,10 @@ final fileCreatedBefore = 2013-10-20T19:20:30+01:00; // DateTime |
 | 
				
			|||||||
final isArchived = true; // bool | 
 | 
					final isArchived = true; // bool | 
 | 
				
			||||||
final isFavorite = true; // bool | 
 | 
					final isFavorite = true; // bool | 
 | 
				
			||||||
final withPartners = true; // bool | 
 | 
					final withPartners = true; // bool | 
 | 
				
			||||||
 | 
					final withSharedAlbums = true; // bool | 
 | 
				
			||||||
 | 
					
 | 
				
			||||||
try {
 | 
					try {
 | 
				
			||||||
    final result = api_instance.getMapMarkers(fileCreatedAfter, fileCreatedBefore, isArchived, isFavorite, withPartners);
 | 
					    final result = api_instance.getMapMarkers(fileCreatedAfter, fileCreatedBefore, isArchived, isFavorite, withPartners, withSharedAlbums);
 | 
				
			||||||
    print(result);
 | 
					    print(result);
 | 
				
			||||||
} catch (e) {
 | 
					} catch (e) {
 | 
				
			||||||
    print('Exception when calling AssetApi->getMapMarkers: $e\n');
 | 
					    print('Exception when calling AssetApi->getMapMarkers: $e\n');
 | 
				
			||||||
@ -546,6 +547,7 @@ Name | Type | Description  | Notes
 | 
				
			|||||||
 **isArchived** | **bool**|  | [optional] 
 | 
					 **isArchived** | **bool**|  | [optional] 
 | 
				
			||||||
 **isFavorite** | **bool**|  | [optional] 
 | 
					 **isFavorite** | **bool**|  | [optional] 
 | 
				
			||||||
 **withPartners** | **bool**|  | [optional] 
 | 
					 **withPartners** | **bool**|  | [optional] 
 | 
				
			||||||
 | 
					 **withSharedAlbums** | **bool**|  | [optional] 
 | 
				
			||||||
 | 
					
 | 
				
			||||||
### Return type
 | 
					### Return type
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
				
			|||||||
							
								
								
									
										13
									
								
								mobile/openapi/lib/api/asset_api.dart
									
									
									
										generated
									
									
									
								
							
							
						
						
									
										13
									
								
								mobile/openapi/lib/api/asset_api.dart
									
									
									
										generated
									
									
									
								
							@ -522,7 +522,9 @@ class AssetApi {
 | 
				
			|||||||
  /// * [bool] isFavorite:
 | 
					  /// * [bool] isFavorite:
 | 
				
			||||||
  ///
 | 
					  ///
 | 
				
			||||||
  /// * [bool] withPartners:
 | 
					  /// * [bool] withPartners:
 | 
				
			||||||
  Future<Response> getMapMarkersWithHttpInfo({ DateTime? fileCreatedAfter, DateTime? fileCreatedBefore, bool? isArchived, bool? isFavorite, bool? withPartners, }) async {
 | 
					  ///
 | 
				
			||||||
 | 
					  /// * [bool] withSharedAlbums:
 | 
				
			||||||
 | 
					  Future<Response> getMapMarkersWithHttpInfo({ DateTime? fileCreatedAfter, DateTime? fileCreatedBefore, bool? isArchived, bool? isFavorite, bool? withPartners, bool? withSharedAlbums, }) async {
 | 
				
			||||||
    // ignore: prefer_const_declarations
 | 
					    // ignore: prefer_const_declarations
 | 
				
			||||||
    final path = r'/asset/map-marker';
 | 
					    final path = r'/asset/map-marker';
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@ -548,6 +550,9 @@ class AssetApi {
 | 
				
			|||||||
    if (withPartners != null) {
 | 
					    if (withPartners != null) {
 | 
				
			||||||
      queryParams.addAll(_queryParams('', 'withPartners', withPartners));
 | 
					      queryParams.addAll(_queryParams('', 'withPartners', withPartners));
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
 | 
					    if (withSharedAlbums != null) {
 | 
				
			||||||
 | 
					      queryParams.addAll(_queryParams('', 'withSharedAlbums', withSharedAlbums));
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    const contentTypes = <String>[];
 | 
					    const contentTypes = <String>[];
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@ -574,8 +579,10 @@ class AssetApi {
 | 
				
			|||||||
  /// * [bool] isFavorite:
 | 
					  /// * [bool] isFavorite:
 | 
				
			||||||
  ///
 | 
					  ///
 | 
				
			||||||
  /// * [bool] withPartners:
 | 
					  /// * [bool] withPartners:
 | 
				
			||||||
  Future<List<MapMarkerResponseDto>?> getMapMarkers({ DateTime? fileCreatedAfter, DateTime? fileCreatedBefore, bool? isArchived, bool? isFavorite, bool? withPartners, }) async {
 | 
					  ///
 | 
				
			||||||
    final response = await getMapMarkersWithHttpInfo( fileCreatedAfter: fileCreatedAfter, fileCreatedBefore: fileCreatedBefore, isArchived: isArchived, isFavorite: isFavorite, withPartners: withPartners, );
 | 
					  /// * [bool] withSharedAlbums:
 | 
				
			||||||
 | 
					  Future<List<MapMarkerResponseDto>?> getMapMarkers({ DateTime? fileCreatedAfter, DateTime? fileCreatedBefore, bool? isArchived, bool? isFavorite, bool? withPartners, bool? withSharedAlbums, }) async {
 | 
				
			||||||
 | 
					    final response = await getMapMarkersWithHttpInfo( fileCreatedAfter: fileCreatedAfter, fileCreatedBefore: fileCreatedBefore, isArchived: isArchived, isFavorite: isFavorite, withPartners: withPartners, withSharedAlbums: withSharedAlbums, );
 | 
				
			||||||
    if (response.statusCode >= HttpStatus.badRequest) {
 | 
					    if (response.statusCode >= HttpStatus.badRequest) {
 | 
				
			||||||
      throw ApiException(response.statusCode, await _decodeBodyBytes(response));
 | 
					      throw ApiException(response.statusCode, await _decodeBodyBytes(response));
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
 | 
				
			|||||||
							
								
								
									
										2
									
								
								mobile/openapi/test/asset_api_test.dart
									
									
									
										generated
									
									
									
								
							
							
						
						
									
										2
									
								
								mobile/openapi/test/asset_api_test.dart
									
									
									
										generated
									
									
									
								
							@ -65,7 +65,7 @@ void main() {
 | 
				
			|||||||
      // TODO
 | 
					      // TODO
 | 
				
			||||||
    });
 | 
					    });
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    //Future<List<MapMarkerResponseDto>> getMapMarkers({ DateTime fileCreatedAfter, DateTime fileCreatedBefore, bool isArchived, bool isFavorite, bool withPartners }) async
 | 
					    //Future<List<MapMarkerResponseDto>> getMapMarkers({ DateTime fileCreatedAfter, DateTime fileCreatedBefore, bool isArchived, bool isFavorite, bool withPartners, bool withSharedAlbums }) async
 | 
				
			||||||
    test('test getMapMarkers', () async {
 | 
					    test('test getMapMarkers', () async {
 | 
				
			||||||
      // TODO
 | 
					      // TODO
 | 
				
			||||||
    });
 | 
					    });
 | 
				
			||||||
 | 
				
			|||||||
@ -1386,6 +1386,14 @@
 | 
				
			|||||||
            "schema": {
 | 
					            "schema": {
 | 
				
			||||||
              "type": "boolean"
 | 
					              "type": "boolean"
 | 
				
			||||||
            }
 | 
					            }
 | 
				
			||||||
 | 
					          },
 | 
				
			||||||
 | 
					          {
 | 
				
			||||||
 | 
					            "name": "withSharedAlbums",
 | 
				
			||||||
 | 
					            "required": false,
 | 
				
			||||||
 | 
					            "in": "query",
 | 
				
			||||||
 | 
					            "schema": {
 | 
				
			||||||
 | 
					              "type": "boolean"
 | 
				
			||||||
 | 
					            }
 | 
				
			||||||
          }
 | 
					          }
 | 
				
			||||||
        ],
 | 
					        ],
 | 
				
			||||||
        "responses": {
 | 
					        "responses": {
 | 
				
			||||||
 | 
				
			|||||||
@ -1442,12 +1442,13 @@ export function runAssetJobs({ assetJobsDto }: {
 | 
				
			|||||||
        body: assetJobsDto
 | 
					        body: assetJobsDto
 | 
				
			||||||
    })));
 | 
					    })));
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
export function getMapMarkers({ fileCreatedAfter, fileCreatedBefore, isArchived, isFavorite, withPartners }: {
 | 
					export function getMapMarkers({ fileCreatedAfter, fileCreatedBefore, isArchived, isFavorite, withPartners, withSharedAlbums }: {
 | 
				
			||||||
    fileCreatedAfter?: string;
 | 
					    fileCreatedAfter?: string;
 | 
				
			||||||
    fileCreatedBefore?: string;
 | 
					    fileCreatedBefore?: string;
 | 
				
			||||||
    isArchived?: boolean;
 | 
					    isArchived?: boolean;
 | 
				
			||||||
    isFavorite?: boolean;
 | 
					    isFavorite?: boolean;
 | 
				
			||||||
    withPartners?: boolean;
 | 
					    withPartners?: boolean;
 | 
				
			||||||
 | 
					    withSharedAlbums?: boolean;
 | 
				
			||||||
}, opts?: Oazapfts.RequestOpts) {
 | 
					}, opts?: Oazapfts.RequestOpts) {
 | 
				
			||||||
    return oazapfts.ok(oazapfts.fetchJson<{
 | 
					    return oazapfts.ok(oazapfts.fetchJson<{
 | 
				
			||||||
        status: 200;
 | 
					        status: 200;
 | 
				
			||||||
@ -1457,7 +1458,8 @@ export function getMapMarkers({ fileCreatedAfter, fileCreatedBefore, isArchived,
 | 
				
			|||||||
        fileCreatedBefore,
 | 
					        fileCreatedBefore,
 | 
				
			||||||
        isArchived,
 | 
					        isArchived,
 | 
				
			||||||
        isFavorite,
 | 
					        isFavorite,
 | 
				
			||||||
        withPartners
 | 
					        withPartners,
 | 
				
			||||||
 | 
					        withSharedAlbums
 | 
				
			||||||
    }))}`, {
 | 
					    }))}`, {
 | 
				
			||||||
        ...opts
 | 
					        ...opts
 | 
				
			||||||
    }));
 | 
					    }));
 | 
				
			||||||
 | 
				
			|||||||
@ -317,6 +317,9 @@ export class MapMarkerDto {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
  @ValidateBoolean({ optional: true })
 | 
					  @ValidateBoolean({ optional: true })
 | 
				
			||||||
  withPartners?: boolean;
 | 
					  withPartners?: boolean;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  @ValidateBoolean({ optional: true })
 | 
				
			||||||
 | 
					  withSharedAlbums?: boolean;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
export class MemoryLaneDto {
 | 
					export class MemoryLaneDto {
 | 
				
			||||||
 | 
				
			|||||||
@ -183,7 +183,7 @@ export interface IAssetRepository {
 | 
				
			|||||||
  softDeleteAll(ids: string[]): Promise<void>;
 | 
					  softDeleteAll(ids: string[]): Promise<void>;
 | 
				
			||||||
  restoreAll(ids: string[]): Promise<void>;
 | 
					  restoreAll(ids: string[]): Promise<void>;
 | 
				
			||||||
  findLivePhotoMatch(options: LivePhotoSearchOptions): Promise<AssetEntity | null>;
 | 
					  findLivePhotoMatch(options: LivePhotoSearchOptions): Promise<AssetEntity | null>;
 | 
				
			||||||
  getMapMarkers(ownerIds: string[], options?: MapMarkerSearchOptions): Promise<MapMarker[]>;
 | 
					  getMapMarkers(ownerIds: string[], albumIds: string[], options?: MapMarkerSearchOptions): Promise<MapMarker[]>;
 | 
				
			||||||
  getStatistics(ownerId: string, options: AssetStatsOptions): Promise<AssetStats>;
 | 
					  getStatistics(ownerId: string, options: AssetStatsOptions): Promise<AssetStats>;
 | 
				
			||||||
  getTimeBuckets(options: TimeBucketOptions): Promise<TimeBucketItem[]>;
 | 
					  getTimeBuckets(options: TimeBucketOptions): Promise<TimeBucketItem[]>;
 | 
				
			||||||
  getTimeBucket(timeBucket: string, options: TimeBucketOptions): Promise<AssetEntity[]>;
 | 
					  getTimeBucket(timeBucket: string, options: TimeBucketOptions): Promise<AssetEntity[]>;
 | 
				
			||||||
 | 
				
			|||||||
@ -490,9 +490,24 @@ export class AssetRepository implements IAssetRepository {
 | 
				
			|||||||
    });
 | 
					    });
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  async getMapMarkers(ownerIds: string[], options: MapMarkerSearchOptions = {}): Promise<MapMarker[]> {
 | 
					  async getMapMarkers(
 | 
				
			||||||
 | 
					    ownerIds: string[],
 | 
				
			||||||
 | 
					    albumIds: string[],
 | 
				
			||||||
 | 
					    options: MapMarkerSearchOptions = {},
 | 
				
			||||||
 | 
					  ): Promise<MapMarker[]> {
 | 
				
			||||||
    const { isArchived, isFavorite, fileCreatedAfter, fileCreatedBefore } = options;
 | 
					    const { isArchived, isFavorite, fileCreatedAfter, fileCreatedBefore } = options;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    const where = {
 | 
				
			||||||
 | 
					      isVisible: true,
 | 
				
			||||||
 | 
					      isArchived,
 | 
				
			||||||
 | 
					      exifInfo: {
 | 
				
			||||||
 | 
					        latitude: Not(IsNull()),
 | 
				
			||||||
 | 
					        longitude: Not(IsNull()),
 | 
				
			||||||
 | 
					      },
 | 
				
			||||||
 | 
					      isFavorite,
 | 
				
			||||||
 | 
					      fileCreatedAt: OptionalBetween(fileCreatedAfter, fileCreatedBefore),
 | 
				
			||||||
 | 
					    };
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    const assets = await this.repository.find({
 | 
					    const assets = await this.repository.find({
 | 
				
			||||||
      select: {
 | 
					      select: {
 | 
				
			||||||
        id: true,
 | 
					        id: true,
 | 
				
			||||||
@ -504,17 +519,10 @@ export class AssetRepository implements IAssetRepository {
 | 
				
			|||||||
          longitude: true,
 | 
					          longitude: true,
 | 
				
			||||||
        },
 | 
					        },
 | 
				
			||||||
      },
 | 
					      },
 | 
				
			||||||
      where: {
 | 
					      where: [
 | 
				
			||||||
        ownerId: In([...ownerIds]),
 | 
					        { ...where, ownerId: In([...ownerIds]) },
 | 
				
			||||||
        isVisible: true,
 | 
					        { ...where, albums: { id: In([...albumIds]) } },
 | 
				
			||||||
        isArchived,
 | 
					      ],
 | 
				
			||||||
        exifInfo: {
 | 
					 | 
				
			||||||
          latitude: Not(IsNull()),
 | 
					 | 
				
			||||||
          longitude: Not(IsNull()),
 | 
					 | 
				
			||||||
        },
 | 
					 | 
				
			||||||
        isFavorite,
 | 
					 | 
				
			||||||
        fileCreatedAt: OptionalBetween(fileCreatedAfter, fileCreatedBefore),
 | 
					 | 
				
			||||||
      },
 | 
					 | 
				
			||||||
      relations: {
 | 
					      relations: {
 | 
				
			||||||
        exifInfo: true,
 | 
					        exifInfo: true,
 | 
				
			||||||
      },
 | 
					      },
 | 
				
			||||||
 | 
				
			|||||||
@ -2,6 +2,7 @@ import { BadRequestException, UnauthorizedException } from '@nestjs/common';
 | 
				
			|||||||
import { mapAsset } from 'src/dtos/asset-response.dto';
 | 
					import { mapAsset } from 'src/dtos/asset-response.dto';
 | 
				
			||||||
import { AssetJobName, AssetStatsResponseDto, UploadFieldName } from 'src/dtos/asset.dto';
 | 
					import { AssetJobName, AssetStatsResponseDto, UploadFieldName } from 'src/dtos/asset.dto';
 | 
				
			||||||
import { AssetEntity, AssetType } from 'src/entities/asset.entity';
 | 
					import { AssetEntity, AssetType } from 'src/entities/asset.entity';
 | 
				
			||||||
 | 
					import { IAlbumRepository } from 'src/interfaces/album.interface';
 | 
				
			||||||
import { IAssetStackRepository } from 'src/interfaces/asset-stack.interface';
 | 
					import { IAssetStackRepository } from 'src/interfaces/asset-stack.interface';
 | 
				
			||||||
import { AssetStats, IAssetRepository } from 'src/interfaces/asset.interface';
 | 
					import { AssetStats, IAssetRepository } from 'src/interfaces/asset.interface';
 | 
				
			||||||
import { ClientEvent, IEventRepository } from 'src/interfaces/event.interface';
 | 
					import { ClientEvent, IEventRepository } from 'src/interfaces/event.interface';
 | 
				
			||||||
@ -18,6 +19,7 @@ import { faceStub } from 'test/fixtures/face.stub';
 | 
				
			|||||||
import { partnerStub } from 'test/fixtures/partner.stub';
 | 
					import { partnerStub } from 'test/fixtures/partner.stub';
 | 
				
			||||||
import { userStub } from 'test/fixtures/user.stub';
 | 
					import { userStub } from 'test/fixtures/user.stub';
 | 
				
			||||||
import { IAccessRepositoryMock, newAccessRepositoryMock } from 'test/repositories/access.repository.mock';
 | 
					import { IAccessRepositoryMock, newAccessRepositoryMock } from 'test/repositories/access.repository.mock';
 | 
				
			||||||
 | 
					import { newAlbumRepositoryMock } from 'test/repositories/album.repository.mock';
 | 
				
			||||||
import { newAssetStackRepositoryMock } from 'test/repositories/asset-stack.repository.mock';
 | 
					import { newAssetStackRepositoryMock } from 'test/repositories/asset-stack.repository.mock';
 | 
				
			||||||
import { newAssetRepositoryMock } from 'test/repositories/asset.repository.mock';
 | 
					import { newAssetRepositoryMock } from 'test/repositories/asset.repository.mock';
 | 
				
			||||||
import { newEventRepositoryMock } from 'test/repositories/event.repository.mock';
 | 
					import { newEventRepositoryMock } from 'test/repositories/event.repository.mock';
 | 
				
			||||||
@ -160,6 +162,7 @@ describe(AssetService.name, () => {
 | 
				
			|||||||
  let configMock: Mocked<ISystemConfigRepository>;
 | 
					  let configMock: Mocked<ISystemConfigRepository>;
 | 
				
			||||||
  let partnerMock: Mocked<IPartnerRepository>;
 | 
					  let partnerMock: Mocked<IPartnerRepository>;
 | 
				
			||||||
  let assetStackMock: Mocked<IAssetStackRepository>;
 | 
					  let assetStackMock: Mocked<IAssetStackRepository>;
 | 
				
			||||||
 | 
					  let albumMock: Mocked<IAlbumRepository>;
 | 
				
			||||||
  let loggerMock: Mocked<ILoggerRepository>;
 | 
					  let loggerMock: Mocked<ILoggerRepository>;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  it('should work', () => {
 | 
					  it('should work', () => {
 | 
				
			||||||
@ -182,6 +185,7 @@ describe(AssetService.name, () => {
 | 
				
			|||||||
    configMock = newSystemConfigRepositoryMock();
 | 
					    configMock = newSystemConfigRepositoryMock();
 | 
				
			||||||
    partnerMock = newPartnerRepositoryMock();
 | 
					    partnerMock = newPartnerRepositoryMock();
 | 
				
			||||||
    assetStackMock = newAssetStackRepositoryMock();
 | 
					    assetStackMock = newAssetStackRepositoryMock();
 | 
				
			||||||
 | 
					    albumMock = newAlbumRepositoryMock();
 | 
				
			||||||
    loggerMock = newLoggerRepositoryMock();
 | 
					    loggerMock = newLoggerRepositoryMock();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    sut = new AssetService(
 | 
					    sut = new AssetService(
 | 
				
			||||||
@ -194,6 +198,7 @@ describe(AssetService.name, () => {
 | 
				
			|||||||
      eventMock,
 | 
					      eventMock,
 | 
				
			||||||
      partnerMock,
 | 
					      partnerMock,
 | 
				
			||||||
      assetStackMock,
 | 
					      assetStackMock,
 | 
				
			||||||
 | 
					      albumMock,
 | 
				
			||||||
      loggerMock,
 | 
					      loggerMock,
 | 
				
			||||||
    );
 | 
					    );
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
				
			|||||||
@ -29,6 +29,7 @@ import { UpdateStackParentDto } from 'src/dtos/stack.dto';
 | 
				
			|||||||
import { AssetEntity } from 'src/entities/asset.entity';
 | 
					import { AssetEntity } from 'src/entities/asset.entity';
 | 
				
			||||||
import { LibraryType } from 'src/entities/library.entity';
 | 
					import { LibraryType } from 'src/entities/library.entity';
 | 
				
			||||||
import { IAccessRepository } from 'src/interfaces/access.interface';
 | 
					import { IAccessRepository } from 'src/interfaces/access.interface';
 | 
				
			||||||
 | 
					import { IAlbumRepository } from 'src/interfaces/album.interface';
 | 
				
			||||||
import { IAssetStackRepository } from 'src/interfaces/asset-stack.interface';
 | 
					import { IAssetStackRepository } from 'src/interfaces/asset-stack.interface';
 | 
				
			||||||
import { IAssetRepository } from 'src/interfaces/asset.interface';
 | 
					import { IAssetRepository } from 'src/interfaces/asset.interface';
 | 
				
			||||||
import { ClientEvent, IEventRepository } from 'src/interfaces/event.interface';
 | 
					import { ClientEvent, IEventRepository } from 'src/interfaces/event.interface';
 | 
				
			||||||
@ -78,6 +79,7 @@ export class AssetService {
 | 
				
			|||||||
    @Inject(IEventRepository) private eventRepository: IEventRepository,
 | 
					    @Inject(IEventRepository) private eventRepository: IEventRepository,
 | 
				
			||||||
    @Inject(IPartnerRepository) private partnerRepository: IPartnerRepository,
 | 
					    @Inject(IPartnerRepository) private partnerRepository: IPartnerRepository,
 | 
				
			||||||
    @Inject(IAssetStackRepository) private assetStackRepository: IAssetStackRepository,
 | 
					    @Inject(IAssetStackRepository) private assetStackRepository: IAssetStackRepository,
 | 
				
			||||||
 | 
					    @Inject(IAlbumRepository) private albumRepository: IAlbumRepository,
 | 
				
			||||||
    @Inject(ILoggerRepository) private logger: ILoggerRepository,
 | 
					    @Inject(ILoggerRepository) private logger: ILoggerRepository,
 | 
				
			||||||
  ) {
 | 
					  ) {
 | 
				
			||||||
    this.logger.setContext(AssetService.name);
 | 
					    this.logger.setContext(AssetService.name);
 | 
				
			||||||
@ -167,6 +169,7 @@ export class AssetService {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
  async getMapMarkers(auth: AuthDto, options: MapMarkerDto): Promise<MapMarkerResponseDto[]> {
 | 
					  async getMapMarkers(auth: AuthDto, options: MapMarkerDto): Promise<MapMarkerResponseDto[]> {
 | 
				
			||||||
    const userIds: string[] = [auth.user.id];
 | 
					    const userIds: string[] = [auth.user.id];
 | 
				
			||||||
 | 
					    // TODO convert to SQL join
 | 
				
			||||||
    if (options.withPartners) {
 | 
					    if (options.withPartners) {
 | 
				
			||||||
      const partners = await this.partnerRepository.getAll(auth.user.id);
 | 
					      const partners = await this.partnerRepository.getAll(auth.user.id);
 | 
				
			||||||
      const partnersIds = partners
 | 
					      const partnersIds = partners
 | 
				
			||||||
@ -174,7 +177,18 @@ export class AssetService {
 | 
				
			|||||||
        .map((partner) => partner.sharedById);
 | 
					        .map((partner) => partner.sharedById);
 | 
				
			||||||
      userIds.push(...partnersIds);
 | 
					      userIds.push(...partnersIds);
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
    return this.assetRepository.getMapMarkers(userIds, options);
 | 
					
 | 
				
			||||||
 | 
					    // TODO convert to SQL join
 | 
				
			||||||
 | 
					    const albumIds: string[] = [];
 | 
				
			||||||
 | 
					    if (options.withSharedAlbums) {
 | 
				
			||||||
 | 
					      const [ownedAlbums, sharedAlbums] = await Promise.all([
 | 
				
			||||||
 | 
					        this.albumRepository.getOwned(auth.user.id),
 | 
				
			||||||
 | 
					        this.albumRepository.getShared(auth.user.id),
 | 
				
			||||||
 | 
					      ]);
 | 
				
			||||||
 | 
					      albumIds.push(...ownedAlbums.map((album) => album.id), ...sharedAlbums.map((album) => album.id));
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    return this.assetRepository.getMapMarkers(userIds, albumIds, options);
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  async getMemoryLane(auth: AuthDto, dto: MemoryLaneDto): Promise<MemoryLaneResponseDto[]> {
 | 
					  async getMemoryLane(auth: AuthDto, dto: MemoryLaneDto): Promise<MemoryLaneResponseDto[]> {
 | 
				
			||||||
 | 
				
			|||||||
@ -30,7 +30,12 @@
 | 
				
			|||||||
    <SettingSwitch id="allow-dark-mode" title="Allow dark mode" bind:checked={settings.allowDarkMode} />
 | 
					    <SettingSwitch id="allow-dark-mode" title="Allow dark mode" bind:checked={settings.allowDarkMode} />
 | 
				
			||||||
    <SettingSwitch id="only-favorites" title="Only favorites" bind:checked={settings.onlyFavorites} />
 | 
					    <SettingSwitch id="only-favorites" title="Only favorites" bind:checked={settings.onlyFavorites} />
 | 
				
			||||||
    <SettingSwitch id="include-archived" title="Include archived" bind:checked={settings.includeArchived} />
 | 
					    <SettingSwitch id="include-archived" title="Include archived" bind:checked={settings.includeArchived} />
 | 
				
			||||||
    <SettingSwitch id="include-shared-with-me" title="Include shared with me" bind:checked={settings.withPartners} />
 | 
					    <SettingSwitch
 | 
				
			||||||
 | 
					      id="include-shared-partner-assets"
 | 
				
			||||||
 | 
					      title="Include shared partner assets"
 | 
				
			||||||
 | 
					      bind:checked={settings.withPartners}
 | 
				
			||||||
 | 
					    />
 | 
				
			||||||
 | 
					    <SettingSwitch id="include-shared-albums" title="Include shared albums" bind:checked={settings.withSharedAlbums} />
 | 
				
			||||||
    {#if customDateRange}
 | 
					    {#if customDateRange}
 | 
				
			||||||
      <div in:fly={{ y: 10, duration: 200 }} class="flex flex-col gap-4">
 | 
					      <div in:fly={{ y: 10, duration: 200 }} class="flex flex-col gap-4">
 | 
				
			||||||
        <div class="flex items-center justify-between gap-8">
 | 
					        <div class="flex items-center justify-between gap-8">
 | 
				
			||||||
 | 
				
			|||||||
@ -47,6 +47,7 @@ export interface MapSettings {
 | 
				
			|||||||
  includeArchived: boolean;
 | 
					  includeArchived: boolean;
 | 
				
			||||||
  onlyFavorites: boolean;
 | 
					  onlyFavorites: boolean;
 | 
				
			||||||
  withPartners: boolean;
 | 
					  withPartners: boolean;
 | 
				
			||||||
 | 
					  withSharedAlbums: boolean;
 | 
				
			||||||
  relativeDate: string;
 | 
					  relativeDate: string;
 | 
				
			||||||
  dateAfter: string;
 | 
					  dateAfter: string;
 | 
				
			||||||
  dateBefore: string;
 | 
					  dateBefore: string;
 | 
				
			||||||
@ -57,6 +58,7 @@ export const mapSettings = persisted<MapSettings>('map-settings', {
 | 
				
			|||||||
  includeArchived: false,
 | 
					  includeArchived: false,
 | 
				
			||||||
  onlyFavorites: false,
 | 
					  onlyFavorites: false,
 | 
				
			||||||
  withPartners: false,
 | 
					  withPartners: false,
 | 
				
			||||||
 | 
					  withSharedAlbums: false,
 | 
				
			||||||
  relativeDate: '',
 | 
					  relativeDate: '',
 | 
				
			||||||
  dateAfter: '',
 | 
					  dateAfter: '',
 | 
				
			||||||
  dateBefore: '',
 | 
					  dateBefore: '',
 | 
				
			||||||
 | 
				
			|||||||
@ -47,7 +47,7 @@
 | 
				
			|||||||
    }
 | 
					    }
 | 
				
			||||||
    abortController = new AbortController();
 | 
					    abortController = new AbortController();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    const { includeArchived, onlyFavorites, withPartners } = $mapSettings;
 | 
					    const { includeArchived, onlyFavorites, withPartners, withSharedAlbums } = $mapSettings;
 | 
				
			||||||
    const { fileCreatedAfter, fileCreatedBefore } = getFileCreatedDates();
 | 
					    const { fileCreatedAfter, fileCreatedBefore } = getFileCreatedDates();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    return await getMapMarkers(
 | 
					    return await getMapMarkers(
 | 
				
			||||||
@ -57,6 +57,7 @@
 | 
				
			|||||||
        fileCreatedAfter: fileCreatedAfter || undefined,
 | 
					        fileCreatedAfter: fileCreatedAfter || undefined,
 | 
				
			||||||
        fileCreatedBefore,
 | 
					        fileCreatedBefore,
 | 
				
			||||||
        withPartners: withPartners || undefined,
 | 
					        withPartners: withPartners || undefined,
 | 
				
			||||||
 | 
					        withSharedAlbums: withSharedAlbums || undefined,
 | 
				
			||||||
      },
 | 
					      },
 | 
				
			||||||
      {
 | 
					      {
 | 
				
			||||||
        signal: abortController.signal,
 | 
					        signal: abortController.signal,
 | 
				
			||||||
 | 
				
			|||||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user