GithubHelp home page GithubHelp logo

brent1lt / p.a.r.c. Goto Github PK

View Code? Open in Web Editor NEW
7.0 3.0 0.0 49.32 MB

P.A.R.C. is a parking-share web app where anyone with a private spot, or driveway, can list it to make it publicly available to others who want to rent that space for various defined periods of time (e.g. hour, day, week, month).

JavaScript 79.46% HTML 1.78% CSS 18.76%

p.a.r.c.'s Introduction

PARC

Live Site

P.A.R.C. is a parking-share web app where anyone with a private spot, or driveway, can list it to make it publicly available to others who want to rent that space for various defined periods of time (e.g. hour, day, week, month).

This project utilizes MongoDB, Express.js, React/Redux and Node.js.

From start to finish, the beta version was completed in 6 days.

Technologies

On the backend, the following technologies were chosen for their ease-of-use and versatility.

  • MongoDB
  • Express.js
  • Node.js
  • Heroku

For the frontend, we used the following libraries to take advantage of their specific features.

  • React -- for it's modular & re-usable components
  • Redux -- for it's global store and dynamic reducers
  • Axios -- for it's backend connection & flexible API calls

Images were hosted using Amazon Web Services (AWS) S3.

Features

  • Users can create and view listings
  • Parking spot listings can be found through a search bar
  • Parking spot listings can be found through an interactive map
  • Users can book parking spots via a dynamic calendar
  • User accounts are secured with hashed & salted passwords
  • Users are able to view & delete their bookings

AWS S3 Integration

Adding Amazon Web Services was a core part of our application and allowed our users to add photos to their listings.

This was especially challenging to implement due to the fact that there are hardly any guides available online. To overcome this, we collaborated with several other developers to help get our buckets operational.

Once functional, it proved to be an integral optimization of our app. It helps with scalability as we don't need to host all of the images in the database, which would subsequently increase server-load.

AWS image

router.post("/image-upload",
  passport.authenticate("jwt", { session: false }),
  upload.single('image'),
  (req, res) => {
      // let photo = res.json({ imageUrl: req.file.location });

    Listing.findOne({street: req.body.street})
        .then(listing => {
          if (listing) {
            return res
              .status(400)
              .json({ address: "This address is already listed" });
          } else {
            const newListing = new Listing({
              user: req.user.id,
              lat: req.body.lat,
              lng: req.body.lng,
              price: req.body.price,
              description: req.body.description,
              street: req.body.street,
              city: req.body.city,
              state: req.body.state,
              zip: req.body.zip,
              photo: req.file.location
            });
            const { isValid, errors } =  validateListingInput(newListing);

            if (!isValid) {
              return res.status(400).json(errors);
            }
            newListing
              .save()
              .then(listing => res.json(listing))
              .catch(err => res.status(400).json(err));
          }
        })
        .catch(err => console.log("FindOne Failed", err));
  }
);

Mapbox GL JS Integration

To display our listings we incorporated the Mapbox GL JS API into our app. Because this library and map use WebGL to render everything, it allowed us the ability to create custom elements and have cross-platform compatibility.

Mapbox Integration

constructor(props) {
  super(props);

  this.state = {
    viewport: {
      // These default LAT & LNG coords are what the map centers on
      latitude: 37.7599034,
      longitude: -122.4183564,
      zoom: 13.25,
      width: '100%',
      height: '50vh',
    },
  };
};

render() {
  if (this.props.listings.length === 0) {
    return (null);
  }

  const { viewport } = this.state;

  const markers = this.props.listings.map((listing) => {
    return (
      <div>
        <Marker
            className="map-marker"
            latitude={listing.lat}
            longitude={listing.lng}
            captureClick={false}
            captureDoubleClick={false}
            captureDrag={false}
          >
            <Pin />
        </Marker>
      </div>
    );
  });

  return (
    <div className="map-container">
      <ReactMapGL
        {...viewport}
        mapStyle="mapbox://styles/mapbox/streets-v11"
        mapboxApiAccessToken={frontendKeys.mapApiKey}
        onViewportChange={(viewport) => this.setState({viewport})}
      >
        {markers}
        <div className="map-nav">
          <NavigationControl
            showCompass={false}
            captureClick={false}
            captureDoubleClick={false}
            captureDrag={false}
            onViewportChange={(viewport) => this.setState({viewport})}
          />
        </div>
      </ReactMapGL>
    </div>
  );
};

AirBNB Calendar API Integration

We integrated AirBNB's calendar API (react-dates) so that we could show a listings currently booked dates, as well as highlight the range of dates that a current user was looking at.

Calendar API

render() {
  if (this.props.bookings === undefined) return null;
  // ITERATE THROUGH THIS.PROPS.BOOKINGS
  // TO CREATE THE MOMENT RANGE OBJECTS AS SEEN BELOW
  const BAD_DATES = [];
  const moment = extendMoment(Moment);

  Object.keys(this.props.bookings).map(booking => (
    BAD_DATES.push(moment.range(
      moment(this.props.bookings[booking].startDate, 'YYYY-MM-DD'),
      moment(this.props.bookings[booking].endDate, 'YYYY-MM-DD')
    ))
  ));

  const isBlocked = day => BAD_DATES.filter(d => d.contains(day, 'day')).length > 0;

  return (
    <div className="booking-form" style={ {width: 400 +'px', height: 400 +'px'} } >
      <h2>Book This Spot</h2>
      <form className='form-booking' onSubmit={ this.handleSubmit }>
        <DateRangePicker
          required={ false }
          small={ true }
          startDate={ this.state.startDate }
          startDateId="start-date-field"
          startDatePlaceholderText="Start Date"
          endDate={ this.state.endDate }
          endDateId="end-date-field"
          endDatePlaceholderText="End Date"
          onDatesChange={ ({ startDate, endDate }) => this.setState({ startDate, endDate }) }
          showClearDates={ true }
          isDayBlocked={ isBlocked }
          focusedInput={ this.state.focusedInput }
          onFocusChange={ focusedInput => this.setState({ focusedInput }) }
          hideKeyboardShortcutsPanel={ true }
        />
        <button className="booking-button">Book Me!</button>
      </form>
      <h2 className="booking-form-error" hidden={!this.state.errors}> { this.renderErrors() } </h2>
    </div>
  );
};

Project Design

When designing P.A.R.C., our goal was to create a quick & stable MERN stack build that utilized an external API (Mapbox). We also wanted to offer an intuitive, friendly and clean user interface & experience. We gave ourselves 6 days to learn the technologies, implement everything and provide a working Beta version.

Future Features & Tasks

  • Add more cities
  • Implement a payment system
  • Google/Apple calendar integration
  • Re-design UI

p.a.r.c.'s People

Contributors

brent1lt avatar samardrey avatar vishal1949 avatar gflujan avatar

Stargazers

Abdullah Al Mashmoum avatar Aram Sargsyan avatar  avatar Nick Howlett avatar  avatar  avatar  avatar

Watchers

 avatar James Cloos avatar  avatar

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.