Skip to content

Conversation

@HalFrgrd
Copy link
Contributor

@HalFrgrd HalFrgrd commented Dec 16, 2024

I really like this plugin and I've been using Templater to query the Google Maps Place API and automatically fill in details like:

Same issue as #173

Solution

A template can contain paths to data returned in the full Google Maps places data
It would be easy to extend the solution to OSM.

Example

With this template:

---
gmaps_place_id: "{{googleMapsPlaceData.place_id}}"
address: "{{googleMapsPlaceData.formatted_address}}"
rating: "{{googleMapsPlaceData.rating}}"
---
#{{googleMapsPlaceData.types.0}}
main type of place: {{googleMapsPlaceData.types.0}}
all types: {{googleMapsPlaceData.types}}
opening_hours: {{googleMapsPlaceData.opening_hours.open_now}}
address: {{googleMapsPlaceData.formatted_address}}

test: {{googleMapsPlaceData.types.99}}
test: {{googleMapsPlaceData.types.99.asdasd}}
test: {{googleMapsPlaceData.opening_hours.open_non_existant_key}}
test: {{googleMapsPlaceData.opening_hours.open_non_existant_key.asdasd}}

A query to Katz's Delicatessen results in this note:
image

Undefined paths return the empty string.

Updating current notes without `place_id` I'm using Templater to update my old geo tagged places that don't have this extra information. In my startup template I have:
templaterPlugin.registerEvent(tp.app.workspace.on('file-open', async (file) => {

    let needs_gmaps_place_id = false;
    let encodedCoords;
    await tp.app.fileManager.processFrontMatter(file, (frontmatter) => {
        needs_gmaps_place_id = ("location" in frontmatter) && !(("gmaps_place_id" in frontmatter));
        if (needs_gmaps_place_id) {
            encodedCoords = encodeURIComponent(frontmatter["location"]);
        }
    });

    if (needs_gmaps_place_id) {
        // Set gmap_place_id if we dont have it set:
        const googleMapsPlacesUrl = `https://maps.googleapis.com/maps/api/geocode/json?latlng=${encodedCoords}&key=[MY API KEY HERE]`
        const googleMapsJsonPlaceId = await tp.web.request(googleMapsPlacesUrl, "results.0.place_id");
        if (googleMapsJsonPlaceId && (googleMapsJsonPlaceId.length > 0)) {
            await tp.app.fileManager.processFrontMatter(file, (frontmatter) => {
                frontmatter["gmaps_place_id"] = googleMapsJsonPlaceId;
            });
        }
    }

    await tp.app.fileManager.processFrontMatter(file, (frontmatter) => {
        if ("location" in frontmatter) {
            const encodedCoords = encodeURIComponent(frontmatter["location"]);

            frontmatter["directions"] = "https://www.google.com/maps/dir/?api=1&destination=" + encodedCoords;
            frontmatter["location_link"] = "https://www.google.com/maps/search/?api=1&query=" + encodedCoords;
            if ("gmaps_place_id" in frontmatter) {
                // We can improve the search!
                const encodedPlaceId = encodeURIComponent(frontmatter["gmaps_place_id"]);
                // frontmatter["directions"] = `${frontmatter["directions"]}&destination_place_id=${encodedPlaceId}`;
                // if you use the coords, google maps doesnt show the name of the place when looking for directions
                frontmatter["directions"] = `https://www.google.com/maps/dir/?api=1&destination=null&destination_place_id=${encodedPlaceId}`;
                frontmatter["location_link"] = `${frontmatter["location_link"]}&query_place_id=${encodedPlaceId}`;
            }
        }
    });
}))

@esm7
Copy link
Owner

esm7 commented Dec 16, 2024

Thank you for this contribution, users will love it.
I added a few minor comments.
Except these, can you add documentation in the README?

@HalFrgrd
Copy link
Contributor Author

HalFrgrd commented Dec 16, 2024

Sure! Do you think unresolvable paths should be left as undefined? Or replaced with an empty string? Or something else?

@HalFrgrd HalFrgrd marked this pull request as ready for review December 16, 2024 22:09
@HalFrgrd
Copy link
Contributor Author

Thank you for this contribution, users will love it. I added a few minor comments. Except these, can you add documentation in the README?

Let me know your comments, I cant see them atm

manifest.json Outdated
{
"id": "obsidian-map-view",
"name": "Map View",
"id": "obsidian-map-view-dev",
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please remove from the PR

src/geosearch.ts Outdated
location: leaflet.LatLng;
resultType: 'searchResult' | 'url' | 'existingMarker';
existingMarker?: FileMarker;
extraLocationData?: object;
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can you make a more specific type here, e.g. define the fields expected from the Google Places API?

src/geosearch.ts Outdated
name: `${result?.name} (${result?.formatted_address})`,
location: geolocation,
resultType: 'searchResult',
extraLocationData: { google_maps_place_data: result },
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is there a reason for using the underscore convention here, which is not consistent with the rest of the code? Rather than googleMapsPlacesData?

src/utils.ts Outdated

export function formatWithTemplates(s: string, query = '') {
function resolveJsonPath(json: object, path: string): string {
// convert a string path like "some.path.to.data.0" to the value at that path in json
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Capital C in 'convert' please, capitals in JSON

src/utils.ts Outdated
// Use regex to find all patterns like {{some.path.to.data.0}}
return inputString.replace(/{{(.*?)}}/g, (_, path: string) => {
const value = resolveJsonPath(json, path);
// return value !== undefined ? value : null;
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If this line is redundant, please remove

src/utils.ts Outdated
let templateContent = '';
if (templatePath && templatePath.length > 0)
templateContent = await app.vault.adapter.read(templatePath);
console.log('extraLocationData:');
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please remove these logs

@esm7
Copy link
Owner

esm7 commented Dec 17, 2024

Thank you for this contribution, users will love it. I added a few minor comments. Except these, can you add documentation in the README?

Let me know your comments, I cant see them atm

So sorry, I forgot to submit the comments after writing them 🤦

@HalFrgrd
Copy link
Contributor Author

I've added the google maps typing package so I can type annotate with google.maps.places.PlaceResult

@esm7 esm7 merged commit 1e0ecca into esm7:master Dec 31, 2024
1 check passed
@esm7
Copy link
Owner

esm7 commented Dec 31, 2024

Looks great, thank you!
I'm currently aiming to not make a 5.2.0 feature release, but a very big 6.0.0 release which I'm working on. So it means it will take at least a couple of weeks until users get this, hope you can do with a local build for now.

@WhyMe4
Copy link

WhyMe4 commented Dec 31, 2024

I was about to ask if anyone had done this.
Question, will this template always create a new note, or could you use it to add to existing note? For example, if I had a note for restaurants, could add multiple businesses/locations on the one note?

@HalFrgrd
Copy link
Contributor Author

I was about to ask if anyone had done this. Question, will this template always create a new note, or could you use it to add to existing note? For example, if I had a note for restaurants, could add multiple businesses/locations on the one note?

Currently only new notes use this new template variable (

templateContent = formatWithTemplates(
). I'm not sure where the inline geolocation handling is done. My guess is to find out where
export async function updateInlineGeolocation(
is called and probably modify that function.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants