技術ブログ |
Developers.IO |
[Tips] Apexで二つのオブジェクトのリストをマージする方法あれこれ |
https://dev.classmethod.jp/articles/tips-how-to-merge-two-lists-of-object-at-apex/
|
tipsapex |
2023-04-18 19:56:58 |
海外TECH |
Ars Technica |
That Galaxy Quest TV series might finally be happening |
https://arstechnica.com/?p=1932765
|
rickman |
2023-04-18 19:52:15 |
海外TECH |
Ars Technica |
Nest 2020 thermostats receive Matter update, which adds Apple Home compatibility |
https://arstechnica.com/?p=1932752
|
models |
2023-04-18 19:33:39 |
海外TECH |
Ars Technica |
Netflix actor wields DMCA takedowns to block tweets sharing “rapey” clip |
https://arstechnica.com/?p=1932755
|
performance |
2023-04-18 19:22:57 |
海外TECH |
MakeUseOf |
Who Is a Red Teamer and How Can You Become One? |
https://www.makeuseof.com/who-is-a-red-teamer-and-how-can-you-become-one/
|
become |
2023-04-18 19:30:17 |
海外TECH |
MakeUseOf |
What Is BMW's E-Ink Exterior, and Why Is It So Revolutionary? |
https://www.makeuseof.com/why-bmw-e-ink-is-revolutionary/
|
customization |
2023-04-18 19:15:16 |
海外TECH |
MakeUseOf |
How to Measure Area and Distance in Google Maps and Google Earth |
https://www.makeuseof.com/tag/measure-area-distance-google-maps-earth/
|
learn |
2023-04-18 19:05:16 |
海外TECH |
MakeUseOf |
What Is the Difference Between a Crypto Wallet and a Crypto Address? |
https://www.makeuseof.com/what-is-the-difference-crypto-wallet-crypto-address/
|
crypto |
2023-04-18 19:01:16 |
海外TECH |
DEV Community |
Modern stack to build a real-time event-driven app |
https://dev.to/bobur/modern-stack-to-build-a-real-time-event-driven-app-56i0
|
Modern stack to build a real time event driven appThe rise of real time event driven applications has led to the development of modern technology stacks that can handle large volumes of events in real time Real time event driven applications are characterized by their ability to respond immediately to events as they occur providing users with up to date information and faster feedback To build a modern stack for a real time event driven application you need to consider several components and technologies that can handle the different stages of event processing from event collection to user interface In this article we will discuss the various components of a modern stack in a real time event driven sample online application architecture that provides discount information from different markets in a city to customers Learning objectivesBy the end of this article you will learn Understand the limitations of continuous polling data from a server Build event driven architecture for a discount web application How to show data to users in real time Understanding the app use cases and requirementsA website or mobile application that provides discount information from different markets in a city to customers can be a useful tool for shoppers who are looking to save money on their purchases The app can provide real time information about discounts and deals in various markets allowing users to quickly and easily find the best deals Below picture shows when we open the website on a mobile app Customers can use this website to compare prices at different markets and receive notifications about discounts and deals at markets that are close to their current location as soon as those markets create real time entries to the system They can use the app to plan their shopping trips and budget their purchases based on the available discounts and deals Some core technical requirements for this app may include It should provide real time information about discounts and deals at various markets ensure that customers have access to the most up to date information and filter out this data based on the user s location Maybe it also should allow users to search for discounts and deals based on specific products or categories Implement user authentication to provide personalized deals information based on the user s preferences Here is an important question arises how do we show real time discount information to users while they are using the website as this data appears in city markets Without diving into many details in this website architecture let s only focus on finding a solution for the technical requirement of retrieving discount data from the server in real time Evaluate the first typical solutionThe first possible straightforward architecture reports discount information by fetching changes from the server based on a timer and shows them on a single page frontend app The page uses a timer to send a request to the server every three seconds to request discounts The response returns an array of discounts which are then displayed to the user This design is known as a timer based polling approach The sample client might use JavaScript libraries such as ReactJS to compose the website UI and the Axios HTTP client to handle requests to a backend API endpoint The backend can be built using REST and any back end framework such as NodeJS or any low code framework The discount information is regularly updated by another integrated API that faces external calls from different markets It can use a webhook endpoint to be notified when new market discounts get available by providing a call back endpoint and then it stores on the server in a relational database MySQL PostgreSQL When our backend discount API is triggered by an HTTP request from the client website it returns content from the database Limitations of the current solutionThe actual issue lies in not how fast we ingest market discount data from data providers but in how fast we deliver it to UI Assuming that data is already stored in our database we analyze and process this data Let s think about some of the weaknesses of this approach Between the discount frontend app and backend service there are constant poll requests for changes Because it is timer based the client application contacts the server whether or not changes exist to the underlying data Once data is returned from the server the entire list of discounts is updated on the web page regardless of any changes in the data This is highly inefficient and calls may result in empty payloads when there haven t been any updates in the database Also what if the called HTTP API accepts our HTTP request but takes a long time to handle it this could affect the user experience especially when the behavior is reflected in the user interface meaning a user has to refresh a page to get the latest changes on discount Once you re more familiar with the first web app architecture and its limitations it s time to introduce a new design to solve the above issues Real Time Event Driven Data ExchangeEvent Driven Architecture EDA seems an ideal fit to achieve the above technical requirements In an event driven architecture components are designed to react to events as they occur rather than being invoked by other components or services Exactly what we want instead of having to constantly poll for changes from the backend it uses a push based approach and lets the backend server send a message or notification to all connected clients automatically Here Real time refers to the ability of our system to respond to events or input immediately or within a very short period of time In the context of the discount web app it means processing discount events as soon as they occur without any significant delay The below diagram shows a new architecture of components in the discount app The architecture shows main stages starting from how we detect discount data change ingest and propagate them to event consumers and show them on the UI Basically it is a reverse flow to the first solution s design Let s break down each component and understand their roles in the next section New architecture breakdownThis new design adds real time features to our discount data reduces traffic and makes a more efficient UI by only updating as data changes But it leverages a few open source technologies and tools for event streaming The first component is a database that acts as a data source which can be PostgreSQL Other popular options include MongoDB or MySQL As data changes in the database a change is detected using the Log based CDC Change Data Capture capabilities of the database It captures the change and records it in a transaction log The captured changes are then transformed into a change event that can be consumed in real time by downstream systems a message broker such as Kafka We will use the Debezium connector for Postgres to extract these CDC logs in the form of event streams from the database to Kafka Once our discount events come into Kafka a streaming database such as RisingWave can subscribe to this change feed from Kafka topics Then RisingWave reads and stores them in its local persistent storage in the form of materialized views to achieve fault tolerance In other words it can act as a stateful stream processor that can materialize the CDC events stream into relational database tables that represent the current state The streaming database helps us quickly build a materialized view in real time that shows all discount information based on user specified matching criteria or prepare statistics like the TOP deals on a chosen product or find out the closest deals from results of different markets Additionally it gives us the ability to analyze the data by delivering them to BI and data analytics platforms for making better business decisions based on our web application usage RisingWave is a streaming database specialized in real time analytics that can read directly database change events from Postgres binlogs or Kafka topics and build a materialized view by joining multiple events together RisingWave will keep the view up to date as new events come and allow you to query using SQL to have access to the latest changes made to the data The streaming database writes back results to Kafka topics by using sink operation in real time Now we need to add JavaScript code to consume and process discount messages received from Kafka and update the UI in real time to display them We can use the KafkaJS library which is a popular Kafka client for Node js to listen and consume Kafka messages Now you can use this Kafka consumer function in a React Native component to update the UI as new discount data is received ConclusionIn this post we learned how to design architecture for a web app that provides real time discount information from different markets The web app can help users find the best deals and make informed shopping decisions We evaluated two different solutions that implement time triggered polling and use even driven patterns We understood that building a modern stack for a real time event driven application requires a range of technologies One can use a combination of streaming processors the streaming database modern JavaScript frameworks and libraries Streaming database deals with complex queries that often change by pre computing the result in its cache In the second architecture we did not introduce any additional service microservice that implements a custom stream processing logic that would result in increased operational overhead and complexity of deployments Related resourcesHow to choose the right streaming databaseIssue SQL queries to manage your dataQuery Real Time Data in Kafka Using SQLHow Change Data Capture CDC Works with Streaming Database Recommended contentIs RisingWave the Right Streaming Database Rethinking Stream Processing and Streaming Databases CommunityJoin the Risingwave Community About the authorVisit my personal blog www iambobur com |
2023-04-18 19:47:51 |
海外TECH |
DEV Community |
FERNtastic Web Development: A Starter's Walkthrough of the FERN Stack |
https://dev.to/wra-sol/ferntastic-web-development-a-starters-walkthrough-of-the-fern-stack-700
|
FERNtastic Web Development A Starter x s Walkthrough of the FERN StackToday I m going to walk you through my set up getting started with the FERN stack that stands for Firebase Express React Node js It s a variant on the incredibly popular MERN stack But you ll see that by swapping out MongoDB for Firebase RTDB we re doing a bit more than swapping out our database provider For the React app we re going to use Vite React Router React Query and Material UI These are my preferences by no means are they necessary The FERN stack is flexible We re going serve a static React app in this walkthrough but this stack sets you up for SSR success just as well For those of you who are unaware Firebase grew from a Chat API as a Service company called Envolve The Founders quickly realized that developers were taking advantage of the powerful real time architecture they had built to power games platforms and other real time services This spun out into Firebase they were acquired by Google in and now offers a whole suite of products to help developers ship quality products quickly Firebase has a whole range of features but in this walk through we re specifically going to be focusing on Firebase Realtime Database and Firebase Authentication This walkthrough assumes a baseline knowledge of Node js and React Getting StartedHop into your favourite IDE and let s get set up Start by making and moving into your project directory and get the project set up mkdir fern stack walkthrough amp amp cd fern stack walkthroughnpm init yNow we ll install express and a few dependencies we re going to need to get started and then make our index file npm install express cors dotenv path url nodemon firebase firebase admintouch index jsI personally like to use ESModules or ECMAScript Modules You can still with Common JS if you prefer but I m going to change my package json to include “ type modules and I m also going to want live refreshes so we ll put in our start script It should look something like this package json name fern stack walkthrough version description main index js type module scripts start nodemon test echo Error no test specified amp amp exit keywords author license ISC dependencies cors dotenv express path url Now that our environment is all set up we can get coding Head over to index js and import the dependancies Take note of how we import dotenv index jsimport express json from express import as dotenv from dotenv import cors from cors Now use those dependancies to start setting up your server index js imports dotenv config const app express const port process env PORT app use cors app use json app get req res gt res send Hello World app listen port gt console log Express app listening on port Alright let s break down what we ve done here First we initialize dotenv This allows us to process variables passed in from the env file We don t have anything in there yet but we will soon Defining what we re calling our server in this case app Defining the PORT that we re running on First we check to see if it s defined in the environment or we default to Telling our app use the Cross Origin Resource Sharing middleware on all routes In production you ll want to be more restrictive with your usage but in development we re going to allow all requests Using the express json middleware on all routes This allows us to retrieve the req body object from any HTTP request with the Content Type application json header Defined our route to return “Hello World Start the app on port and listen for HTTP requests Fire it up with a quick npm run start and you should see something a little like this gt fern stack walkthrough start gt nodemon nodemon nodemon to restart at any time enter rs nodemon watching path s nodemon watching extensions js mjs json nodemon starting node Express app listening on Congratulations Your server is up and running You can now navigate to http localhost and you should see something that looks like this Front end setupNow that we have our server up and running let s start building our front end Open a new terminal window in your IDE and let s get started with our client npm create vite latest client template reactcd clientNow before we fire it up let s install our dependancies npm install mui material emotion react emotion styled mui icons material react router dom react query firebaseNow that the dependancies are all installed head over to the vite config js and we will proxy our API requests to the backend It should look a little something like this vite config jsimport react from vitejs plugin react export default plugins react server proxy api target http localhost changeOrigin true rewrite path gt path replace api This is our config file for our vite server Here we re telling vite to proxy any requests made to api should be sent through to our express app at Port make sure you define the correct port Now by default the Vite template has a lot in it We can safely get rid of the App css file anything in the public folder anything in the assets folder as well as the majority of the index css and App jsx files At this point your entire directory should look like index js package json package lock json node modules client index html vite config js public node modules src assets App jsx index css main jsx client src App jsximport useState from react function App return lt div className App gt lt h gt FERN lt h gt lt div gt export default App client src main jsximport React from react import ReactDOM from react dom client import App from App import index css ReactDOM createRoot document getElementById root render lt React StrictMode gt lt App gt lt React StrictMode gt client src index css body margin display flex min width px min height vh And with that your website should now look like…this Pages and RoutingWe ll work on that soon For now we have the App running and we can start getting our pages together For now we re going to build some very basic pages We ll revisit them once we ve set up a but more code Create a new folder src pages and create the following very basic pages Home jsxconst Home gt return lt h gt Home lt h gt export default Home About jsxconst About gt return lt h gt About lt h gt export default About Login jsxconst Login gt return lt h gt Login lt h gt export default Login Now that we have our pages we have to render them Head back to your App jsx and we ll set it up to import our pages and display them to the user App jsximport React useState useEffect Suspense from react import BrowserRouter as Router Route Routes from react router dom const App gt const routes setRoutes useState useEffect gt function loadPages const context import meta globEager pages jsx const routeList for const path in context const module context path const pageName path replace pages replace jsx const routePath pageName Home pageName toLowerCase const route path routePath component module default routeList push route setRoutes routeList loadPages return lt Router gt lt Suspense fallback lt div gt Loading lt div gt gt lt Routes gt routes map route index gt lt Route key index path route path element lt route component gt gt lt Routes gt lt Suspense gt lt Router gt export default App Ok WOAH That s a lot of changes Let s go through how we went from our simple line App jsx file to that Right away you ll notice we re importing quite a bit more from the React library including the Suspense component which allows us to display a fallback component until the children have loaded In this case we re waiting for the Routes to load Once they are loaded we map them into the React Router component which uses the browser location and renders the associated component lt Router gt lt Suspense fallback lt div gt Loading lt div gt gt lt Routes gt routes map route index gt lt Route key index path route path element lt route component gt gt lt Routes gt lt Suspense gt lt Router gt But where did we load those components That s what the useEffect is for In there we take advantage of the Vite import meta globEager to import any component that we create in our pages directory That means if you create an src pages Contact component you ll also automatically have a page at https localhost PORT contact From there we iterate over each path that we ve found in our pages directory and we assign the Pages with names by removing the jsx extension and changing it to lowercase We also replace Home with so that it navigates to our Homepage component at the root We then use the setRoutes function to update the state with our newly created pages and render them in the previously shows code useEffect gt function loadPages const context import meta globEager pages jsx Imports all components in the pages directory const routeList for const path in context const module context path const pageName path replace pages replace jsx const routePath pageName Home pageName toLowerCase const route path routePath component module default pageName routeList push route setRoutes routeList loadPages It s important to remember that useEffect is a React Hook that lets you synchronize a component with an external system and should be used for that purpose In this case the external system is the import meta globEager which is a special Vite method that occurs asynchronously You can now visit Home About about and Login Login and you ll be greeted with the very basic titles Now that we have our pages set up let s start making things a bit more pretty Getting started with Material UIWhile we really haven t gotten into the meat of what we re doing in terms of integration with Firebase and Auth quite yet I m the type of person who simply can t work in LoFi I don t need it to be high design but let s start establishing our pages We re going to start by creating a Layout context This will enable us to keep our “always on components as well as our theme well defined and easily accessible Start by creating a new src contexts folder and create a new PageLayout jsx file PageLayout jsximport Grid from mui material Grid import Container from mui material Container const PageLayout children gt lt Grid container direction column minHeight vh gt lt Grid item xs py gt lt Container component main gt children lt Container gt lt Grid gt lt Grid gt export default PageLayoutWhat we ve made here is a context component It accepts the children which are nested inside of it and applies it s context universally We simply have to head over to our App jsx and wrap our pages in it Now every one of our pages will have consistent spacing and basic layout But let s make this a bit more powerful We re going to use our context to add a universal Navigation Bar and a Footer providing users with a consistent browsing experience App jsximport PageLayout from contexts PageLayout Other codereturn lt Router gt lt PageLayout gt lt Suspense fallback lt div gt Loading lt div gt gt lt Routes gt routes map route index gt lt Route key index path route path element lt route component gt gt lt Routes gt lt Suspense gt lt PageLayout gt lt Router gt PageLayout jsximport AppBar from mui material AppBar import Toolbar from mui material Toolbar import Typography from mui material Typography import Grid from mui material Grid import Container from mui material Container const Navbar gt lt AppBar position static gt lt Toolbar gt lt Typography variant h component div gt My App lt Typography gt lt Toolbar gt lt AppBar gt const Footer gt lt Grid item xs sx py mt auto backgroundColor fff gt lt Container maxWidth sm gt lt Typography variant body color text secondary align center gt new Date getFullYear My first FERN App lt Typography gt lt Container gt lt Grid gt const PageLayout children gt lt Grid container direction column minHeight vh gt lt Grid item xs gt lt Navbar gt lt Grid gt lt Grid item xs py gt lt Container component main gt children lt Container gt lt Grid gt lt Footer gt lt Grid gt export default PageLayout So in here we ve imported the necessary components from MUI we ve created a Footer which fetches the current year and returns it as our copyright date we ve built a Nav Bar we ll get to the “Nav part soon and we ve added those components into our PageLayout If everything was implemented correctly it should look like this So that s at least an improvement over the white blank page we were seeing earlier But now that we have the Nav Bar in place it should at least have some functionality In App jsx update the PageLayout component and pass in the our routes state and update the PageLayout jsx to pass the routes into the NavBar App jsx lt Router gt lt PageLayout routes routes gt Routes lt PageLayout gt lt Router gt Now we can access the routes in the NavBar object and set it up to help us actually navigate Now once we re done our NavBar component is going to be quite large PageLayout jsxconst PageLayout children routes gt lt Grid container direction column minHeight vh gt lt Grid item xs gt lt Navbar routes routes gt lt Grid gt lt Grid item xs py gt lt Container component main gt children lt Container gt lt Grid gt lt Footer gt lt Grid gt Before we start building it out any further let s move it into it s own functional component Create the src components directory and then the NavBar jsx file inside Update your PageLayout jsx to look like this PageLayout jsximport Typography from mui material Typography import Grid from mui material Grid import Container from mui material Container import Navbar from components NavBar const Footer gt lt Grid item xs sx py mt auto backgroundColor fff gt lt Container maxWidth sm gt lt Typography variant body color text secondary align center gt new Date getFullYear My first FERN App lt Typography gt lt Container gt lt Grid gt const PageLayout children routes gt lt Grid container direction column minHeight vh gt lt Grid item xs gt lt Navbar routes routes gt lt Grid gt lt Grid item xs py gt lt Container component main gt children lt Container gt lt Grid gt lt Footer gt lt Grid gt export default PageLayout And we ll build our our NavBar component Currently it should look something like this components NavBar jsximport AppBar from mui material AppBar import Toolbar from mui material Toolbar import Typography from mui material Typography const Navbar gt lt AppBar position static gt lt Toolbar gt lt Typography variant h component div gt My App lt Typography gt lt Toolbar gt lt AppBar gt We re going to update this component by accepting the routes prop Creating a Menu and iterating over each of the routes to create a menu item const Navbar routes gt return lt AppBar position static gt lt Toolbar gt lt Typography variant h component div gt My App lt Typography gt lt IconButton edge end sx ml auto gt lt MenuIcon gt lt IconButton gt lt Menu gt routes map route index gt return lt MenuItem key index component Link to route path onClick handleMenuClose gt route pageName lt MenuItem gt lt Menu gt lt Toolbar gt lt AppBar gt In here we have created our Menu iterated over each of the menu items and used the pageName of each route as the item Now we need to add some logic to this to make it actually work const Navbar routes gt const navMenuAnchorEl setNavMenuAnchorEl useState null const handleMenuClick e gt setNavMenuAnchorEl e currentTarget const handleMenuClose gt setNavMenuAnchorEl null lt Menu anchorEl navMenuAnchorEl open navMenuAnchorEl MenuListProps onMouseLeave handleMenuClose gt Here we have defined our handleMenuClick to assign our Menu s Anchor Element to the clicked button icon as our navMenuAnchorEl We have created the logic to open the menu when navMenuAnchorEl isn t nullish and when our mouse exits the Menu hover it will close the menu by resetting the anchorEl state Ok awesome But we probably don t want our homepage in there Let s use the “My App on the left to navigate home and remove the Home item from our popover menu return lt AppBar position static gt lt Toolbar gt lt Typography variant h component Link to sx textDecoration none color white gt My App lt Typography gt lt IconButton edge end onClick handleMenuClick sx ml auto gt lt MenuIcon gt lt IconButton gt lt Menu anchorEl navMenuAnchorEl open navMenuAnchorEl MenuListProps onMouseLeave handleMenuClose gt routes map route index gt if route path return return lt MenuItem key index component Link to route path onClick handleMenuClose gt route pageName lt MenuItem gt lt Menu gt lt Toolbar gt lt AppBar gt We ve added the Link component to our Typography in order to keep it the expected colour In our Menu component we are skipping any routes that navigate back to you could also use if route pageName Home if you prefer Same effect Great Now we have some basics in place Let s start building our Auth logic Firebase Auth IntegrationFirebase Auth is a massively powerful drop in solution with OAuth support support for Sign in with Google Twitter SSO SAML and basic username and password That s what we re going to be using here To get started head over to console firebase google com and create a new Project Click on the Web icon give your app a name and then on the next page you should see the instructions to add the Firebase SDK We re going to take these values and create our Firebase instance for our app In src create a new firebaseConfig js It will look something like this src firebaseConfig jsimport initializeApp from firebase app import getDatabase from firebase database const firebaseConfig apiKey YOUR API KEY authDomain YOUR PROJECT firebaseapp com projectId YOUR PROJECT storageBucket YOUR PROJECT appspot com messagingSenderId YOURID appId YOURAPPID databaseURL const app initializeApp firebaseConfig const auth getAuth app const db getDatabase app export app auth db So here we have set up our Firebase App app our Auth and our db all in one file To create your RTDB in Firebase navigate to Build ⇒Realtime Database You ll then be presented with the Database URL which you can populate into your firebaseConfig js Take this time to also set up Authentication For this Walkthrough you will need to activate Email Password sign in Now we re going to wrap our App in the Auth Create a new file in src contexts called AuthProvider jsx Much like our PageLayout jsx this is a Context which will provide our User s auth status to the entire application src contexts AuthProvider jsximport React createContext useState useEffect from react import auth from firebaseConfig export const AuthContext createContext export const AuthProvider children gt const currentUser setCurrentUser useState null useEffect gt const unsubscribe auth onAuthStateChanged user gt setCurrentUser user return gt unsubscribe return lt AuthContext Provider value currentUser gt children lt AuthContext Provider gt So here we are creating a context which all of the child elements can read from and manipulate We re using the useEffect hook to listen for any changes in the authentication state and keeping the context up to date with the currentUser When the component is unmounted or the effect dependencies change we remove the observer by calling the unsubscribe function And just like with our PageLayout jsx we re going to wrap the App in this context App jsx other importsimport AuthProvider from contexts AuthProvider other codereturn lt Router gt lt AuthProvider gt lt PageLayout routes routes gt lt Suspense fallback lt div gt Loading lt div gt gt lt Routes gt routes map route index gt lt Route key index path route path element lt route component gt gt lt Routes gt lt Suspense gt lt PageLayout gt lt AuthProvider gt lt Router gt Now that we have our AuthProvider in place let s create our Sign in and Sign Up page Let s start by creating our Login In and Sign Up forms LoginForm jsximport React useState from react import getAuth signInWithEmailAndPassword from firebase auth import useNavigate from react router dom import TextField Button Typography from mui material const LoginForm gt const email setEmail useState const password setPassword useState const navigate useNavigate const auth getAuth const handleSignIn async e gt e preventDefault try await signInWithEmailAndPassword auth email password navigate dashboard catch error console error Error signing in error return lt form onSubmit handleSignIn gt lt Typography variant h gt Sign In lt Typography gt lt TextField type email label Email variant outlined value email onChange e gt setEmail e target value fullWidth margin normal gt lt TextField type password label Password variant outlined value password onChange e gt setPassword e target value fullWidth margin normal gt lt Button type submit variant contained color primary fullWidth gt Sign In lt Button gt lt form gt export default LoginForm components SignUpForm jsximport React useState useContext from react import auth from firebaseConfig import AuthContext from contexts AuthProvider import useNavigate from react router dom import TextField Button Typography from mui material const SignUpForm gt const email setEmail useState const password setPassword useState const currentUser useContext AuthContext const navigate useNavigate const handleSignUp async e gt e preventDefault try await auth createUserWithEmailAndPassword email password navigate catch error console error Error signing up error return lt form onSubmit handleSignUp gt lt Typography variant h gt Sign Up lt Typography gt lt TextField type email label Email variant outlined value email onChange e gt setEmail e target value fullWidth margin normal gt lt TextField type password label Password variant outlined value password onChange e gt setPassword e target value fullWidth margin normal gt lt Button type submit variant contained color primary fullWidth gt Sign Up lt Button gt lt form gt export default SignUpForm Both of these components are relatively straightforward We re importing the firestore auth library and getting our up to date Auth object which we can then use to Log in or Sign up Now we need to render these at our Login Page Login jsximport React useState from react import Box Button Paper from mui material import LoginForm from components LoginForm import SignUpForm from components SignUpForm const Login gt const showLoginForm setShowLoginForm useState true const handleToggleForm gt setShowLoginForm showLoginForm return lt Box display flex flexDirection column alignItems center gt lt Paper elevation sx p gt showLoginForm lt LoginForm gt lt SignUpForm gt lt Box mt gt lt Button onClick handleToggleForm gt showLoginForm Don t have an account Sign up Already have an account Sign in lt Button gt lt Box gt lt Paper gt lt Box gt export default Login Here we ve imported the Login and Signup form and we re using a basic state to determine which form is being rendered We have our handler function which when clicked simple changes the state from it s current state to the opposite Then depending on the state we either render the Sign Up or Login Form It should look like this Now before you go and test this out we have to make sure there s a way that we re testing it s success Right now both the Sign up and Log In forms redirect you to the Home page after a successful sign in That s not really helpful We re going to create another context This one will help to verify that the user is signed in and if they aren t we ll shoot them off to the login page Let s create another file in src context this one called PrivatePage jsx PrivatePage jsximport useContext from react import Navigate from react router dom import AuthContext from AuthProvider const PrivatePage component Component rest gt const currentUser useContext AuthContext return currentUser lt Component rest gt lt Navigate to login replace gt export default PrivatePage So here we ve imported the AuthContext we re accepting the component and any passed props …rest verifying that the currentUser exists which means they re signed in otherwise redirecting them to the login page We re also going to want to create a Private page which is only accessible to a logged in user Let s create pages Dashboard jsx Dashboard jsximport React useContext from react import Box Typography from mui material import AuthContext from contexts AuthProvider const Dashboard gt const currentUser useContext AuthContext return lt Box display flex flexDirection column alignItems center gt lt Typography variant h mb gt Welcome to the Dashboard lt Typography gt lt Typography variant h mb gt currentUser Logged in as currentUser email lt Typography gt lt Box gt export default Dashboard This component will display the logged in User s email address with a very basic welcome message Since we want this to be a Private Page only accessible to signed in users we re going to have to specify it in our App jsx file App jsximport PrivatePage from contexts PrivatePage useEffect gt function loadPages const context import meta globEager pages jsx const routeList for const path in context const module context path const pageName path replace pages replace jsx const routePath pageName Home pageName toLowerCase const isPrivate pageName Dashboard Set isPrivate to true for Dashboard or other private pages const route path routePath component module default pageName isPrivate routeList push route setRoutes routeList loadPages lt Routes gt routes map route index gt route isPrivate lt Route key index path route path element lt PrivatePage component route component gt gt lt Route key index path route path element lt route component gt gt lt Routes gt Now if we try to navigate to dashboard without a user logged in it will redirect us back to the homepage We have a great way of knowing if we re successfully logged in Let s update our Login and Sign Up forms to redirect us there after successful login or sign up LoginForm jsxconst handleSignIn async e gt e preventDefault try await currentUser signInWithEmailAndPassword email password navigate dashboard Updated with new location catch error console error Error signing in error SignUpForm jsxconst handleSignUp async e gt e preventDefault try await currentUser createUserWithEmailAndPassword email password navigate dashboard Updated with new location catch error console error Error signing up error Once you have those completed go sign up and try it out If you re logged in and everything is set up correctly you should see something like this Now right away you ll notice we forgot to include a way to sign out Let s create that function right now Update the AuthProvider jsx to include import useNavigate from react router dom export const AuthProvider children gt const navigate useNavigate const signOut gt auth signOut navigate login return lt AuthContext Provider value currentUser signOut gt children lt AuthContext Provider gt Now we can call signOut from any of our elements or pages within the provider A natural place to add this is in the NavBar Menu Update the NavBar to import the Auth Context and add the Sign Out menu item NavBar jsximport useState useContext from react import AuthContext from contexts AuthProvider const Navbar routes gt const signOut useContext AuthContext Handlersreturn lt AppBar position static gt lt Toolbar gt lt Typography variant h component Link to sx textDecoration none color white gt My App lt Typography gt lt IconButton edge end onClick handleMenuClick sx ml auto gt lt MenuIcon gt lt IconButton gt lt Menu anchorEl navMenuAnchorEl open navMenuAnchorEl MenuListProps onMouseLeave handleMenuClose gt routes map route index gt if route path return return lt MenuItem key index component Link to route path onClick handleMenuClose gt route pageName lt MenuItem gt lt MenuItem onClick signOut gt lt Menu gt lt Toolbar gt lt AppBar gt Something you might have noticed now our Menu is getting a little bit cluttered We re displaying Login even when a user is signed in and we have a Sign Out even if a user isn t signed in Let s clean up this Menu a bit We really want to be able to Navigate to the About page the Login Page if not logged in and the Sign Out should be available if logged in We ll include the Dashboard link in there as well It s a nice consistent way to navigate around NavBar jsximport useState useContext from react import AppBar Toolbar Typography Menu MenuItem IconButton from mui material import MenuIcon from mui icons material Menu import Link from react router dom import AuthContext from contexts AuthProvider const Navbar gt const signOut currentUser useContext AuthContext const navMenuAnchorEl setNavMenuAnchorEl useState null const handleMenuClick e gt setNavMenuAnchorEl e currentTarget const handleMenuClose gt setNavMenuAnchorEl null return lt AppBar position static gt lt Toolbar gt lt Typography variant h component Link to sx textDecoration none color white gt My App lt Typography gt lt IconButton edge end onClick handleMenuClick sx ml auto gt lt MenuIcon gt lt IconButton gt lt Menu anchorEl navMenuAnchorEl open navMenuAnchorEl MenuListProps onMouseLeave handleMenuClose gt lt MenuItem component Link to about gt About lt MenuItem gt lt MenuItem component Link to dashboard gt Dashboard lt MenuItem gt currentUser lt MenuItem onClick signOut gt Sign out lt MenuItem gt lt MenuItem component Link to login gt Log In lt MenuItem gt lt Menu gt lt Toolbar gt lt AppBar gt export default Navbar Now we ve neatly defined the Menu Items and our NavBar is tidy consistent and contextual We have a Dashboard for our customers and we have our Auth all set up Now Let s get some data entry and manipulation in here Setting up the DatabaseWe ve spent a good amount of time working in React now It seems like a great time to navigate back up a level and head into our server Last we left it it looked like this index jsimport express json from express import as dotenv from dotenv import cors from cors dotenv config const app express const port process env PORT app use cors app use json app get req res gt res send Hello World app listen port gt console log Express app listening on port We re going to now set this up act as our API for our front end We re going to create endpoints to send and retrieve data as well as validate our user request is authentic Just as we did in the React front end we re going to set up our Firebase instance In the root of your app create firebase js firebase jsimport initializeApp from firebase app import getDatabase from firebase database import getAuth from firebase auth const firebaseConfig apiKey YOUR API KEY authDomain YOUR PROJECT firebaseapp com projectId YOUR PROJECT storageBucket YOUR PROJECT appspot com messagingSenderId YOURID appId YOURAPPID databaseURL const firebase initializeApp firebaseConfig const auth getAuth firebase const db getDatabase firebase export firebase auth db You ll notice that we named this instance firebase instead of app That s to avoid collisions with our express app in index js where we will import our app ensuring it s initialized as soon as the app starts We re going also going to define two routes one GET one POST both to data We ll start by defining the routes In your root directory create userRoutes js import express from express const router express Router import db from firebase js import ref set get child from firebase database router get data async req res next gt const userId req body try get ref db users userId then snapshot gt if snapshot exists console log snapshot val res status json snapshot val else console log No data available res sendStatus catch error next new Error error message router post data async req res next gt const userId userData req body try await set ref db users userId userData id userData then gt res status json userData catch e gt throw e catch error next new Error error message export default router Here we are defining our data routes In our GET route we are checking the body for the userId and then returning a snapshot of the data in the database under that user ID For the POST route we are extracting userId and userData in similar fashion then setting the data We also return the userData object for validation on the client side You will see here we are also passing the errors to next We re going to set up central error handling in our index js This helps us keep our code clean performant and readable index jsimport express json from express import as dotenv from dotenv import cors from cors import firebase from firebase js import userRoutes from userRoutes js dotenv config const app express const port process env PORT app use cors app use json app use userRoutes app use req res next gt console log req baseUrl req method next app use error req res next gt res status json error error message app listen port gt console log Express app listening on port Now if you head to Postman you should be able to post to localhost data with a data structured like this And you ll be able to set some test data to read Send a GET and it will retrieve each post But wait I hear you calling out I don t want to use a userId every call And this isn t very secure You re right voice of public opinion You can t set a body on a post route and query params are lame userId testUser userData foo bar id key item testUser foo bar id key item Verify Token MiddlewareWe need a way to consistently validate that the user is who they say they are and to access their userId in an easy uniform fashion First we re going to need to get our Firebase Admin credentials In the Firebase console navigate to Project settings Service accounts and click Generate Key Create a new serviceAccount json at your project root make sure to add this to your gitignore and copy the contents of the download into that file Now that we have our service account credentials we can initialize our Admin app and create our middleware Make a new directory called middlewares and create a file called verifyToken js The verifyToken js is fairly straightforward import admin from firebase admin import serviceAccount from serviceAccount json assert type json admin initializeApp credential admin credential cert serviceAccount const verifyToken async req res next gt const token req headers authorization split Bearer if token return res status send Unauthorized try const decodedToken await admin auth verifyIdToken token req body user decodedToken req body userId decodedToken uid next catch error console error error res status send Forbidden export default verifyToken We import the service account initialize our Admin app then use it to decode the Bearer token that we will pass in with our front end API call This also extracts the decodedToken and sets the req user with the decodedToken object We can then access the whole token object at req body user and the userId at req body userId Now we have somewhere that will store data a way to read that data and a way verify that the user requesting the data is who they say they are Let s head back to the Front End and build out our requests Connecting the Front end and Back endAlright we have our Back end ready to go now we need to input and display our data entries i ve been thinking about building a better grocery app for a while now so I ll start here Because we were so ambiguous in how we defined our back end it s incredibly flexible on the front end The only mandatory field we must pass is an ID With that in mind let s get to work Earlier we very briefly mentioned React Query Let s talk a bit more about why it s so great The big ones for me It handles caching and background updates some of the biggest headaches in development solved It works with any promise As a result it s an exceptional state manager You don t need to write repetitive and annoying reducers you just tell React Query where to get the data and it gets it You might not see why those are so powerful right away but as your projects grow you ll want a good way to share stateful data between components React Query helps with that a lot First we re going to update our App jsx to include our Query Client Provider App jsx other importsimport QueryClient QueryClientProvider from react query const App gt Other code here const queryClient new QueryClient return lt Router gt lt QueryClientProvider client queryClient gt lt AuthProvider gt lt PageLayout routes routes gt lt Suspense fallback lt div gt Loading lt div gt gt lt Routes gt routes map route index gt route isPrivate lt Route key index path route path element lt PrivatePage component route component gt gt lt Route key index path route path element lt route component gt gt lt Routes gt lt Suspense gt lt PageLayout gt lt AuthProvider gt lt QueryClientProvider gt lt Router gt Now we re setting up our queryClient with no options but you can customize this to suit your needs You can define cacheTimes staleTimes and even throw universal errors from your QueryProvider or on a per “useQuery or per “useMutation instance Now that we have that set up let s start building our Queries and Mutations Since we re building a grocery list App we re going to need to add our items Let s start by defining our fetch function Create a new folder src api and make a file called addGroceryItem jsjsxexport const addGroceryItem async groceryItem token gt const response await fetch data method POST headers Content Type application json Authorization Bearer token body JSON stringify userData groceryItem if response ok throw new Error Error adding grocery item response statusText const data await response json return data Here we have defined a a function which accepts a passed in groceryItem and token which we are then sending to our back end for retention Now we want to use this with our React Query Provider so we re going to build a custom Hook to handle this mutation Let s create src hooks and create useAddGroceryItem js jsx useAddGroceryItem jsimport useMutation from react query import addGroceryItem from api addGroceryItem export const useAddGroceryItem token gt const mutation useMutation groceryItem gt addGroceryItem groceryItem token onError error gt console log An error occurred while adding the grocery item error onSuccess data gt console log Grocery item added successfully data return mutation Now that we have everything set up to post a grocery item let s build our logic to fetch our grocery items Much like the above we ll create fetchGroceryItems jsjsx api fetchGroceryItems jsexport const fetchGroceryItems async token gt const response await fetch data method GET headers Content Type application json Authorization Bearer token if response ok throw new Error Error fetching grocery items response statusText const data await response json return data And again like the above we will create our useFetchGroceryItems js hook jsx hooks useFetchGroceryItems jsimport useQuery from react query import fetchGroceryItems from api grocery export const useFetchGroceryItems token gt return useQuery groceryItems gt fetchGroceryItems token I want to take a second to pause here and reflect on what s happening here We have defined functions which mutates data and which returns it React Query doesn t care what this data is where it comes from or how we choose to display it It just needs to receive a Promise and optionally an Error In this case we are polling our data route which we set up earlier but you can and likely will use it for all kinds of state and data management Next up we re going to build our input form and display it in our Dashboard I m going to create a new component called GroceryItemInputForm jsx jsximport React useState from react import TextField from mui material TextField import MenuItem from mui material MenuItem import Button from mui material Button import Grid from mui material Grid const commonMeasurements piece fluid ounce cup pint quart gallon milliliter liter ounce pound gram kilogram const GroceryItemInputForm token gt const name setName useState const quantity setQuantity useState const measurement setMeasurement useState const handleSubmit e gt e preventDefault console log name quantity measurement return component form onSubmit handleSubmit noValidate autoComplete off container justifyContent space between rowGap gt item component TextField label Item Name value name onChange e gt setName e target value xs sm fullWidth gt item component TextField label Quantity value quantity onChange e gt setQuantity e target value fullWidth xs gt item component TextField select label Measurement value measurement onChange e gt setMeasurement e target value sm xs fullWidth gt commonMeasurements map unit gt unit quantity gt s component Button type submit variant contained color primary item xs sm gt Add export default GroceryItemInputForm Here we ve used MUI s Grid to build a nice responsive form which includes a dropdown menu for various common measurements Right away this just logs the entry for us but it s a great start We ll import this into our Dashboard jsx for use where we ll also pass in the user token To make sure we re using the most recent token we re going to get it from the firebase auth library using the getAuth method jsx Dashboard jsximport React useContext from react import Box Typography from mui material import getAuth from firebase auth import GroceryItemInputForm from components GroceryItemInputForm const Dashboard gt const currentUser getAuth return lt Box display flex flexDirection column alignItems center gt lt Typography variant h mb gt Welcome to the Dashboard lt Typography gt lt Typography variant h mb gt currentUser Logged in as currentUser email lt Typography gt lt GroceryItemInputForm token currentUser accessToken gt lt Box gt export default Dashboard Perfect it s now imported into the dashboard which should look like this Now let s hook it up to our API Head back into the GroceryItemInputForm jsx lets import our custom useAddGroceryItem hook jsximport useAddGroceryItem from hooks useAddGroceryItem Then inside the GroceryItemInputForm component we re going to accept the passed token and create our authenticated mutation instance jsx components GroceryItemInputForm jsx Other Codeconst GroceryItemInputForm token gt const name setName useState const quantity setQuantity useState const measurement setMeasurement useState const addGroceryItemMutation useAddGroceryItem token const handleSubmit e gt e preventDefault const newItem name quantity measurement id Date now addGroceryItemMutation mutate newItem onSuccess gt setName setQuantity setMeasurement Other Code Awesome Now we can update our grocery list using our form Notice that we ve also included the onSuccess handler which in this case resets the form back to default You can use this to display a success message navigate users as needed and others You also have available the onError which which can offer error handling on a per mutation instance and onSettled which runs regardless of Success or Error Read more about Mutations and side effects here Now that we have a way to set our grocery list we need a way to display our Grocery items Lets create the GroceryList jsx component jsx GroceryList jsximport React from react import useFetchGroceryItems from hooks useFetchGroceryItems import CircularProgress ListItem ListItemText Typography Grid List from mui material const GroceryList token gt const data groceryItems error isLoading useFetchGroceryItems token if isLoading return if error return Error error message return Object values groceryItems map item gt primary item name secondary item quantity item measurement gt export default GroceryList Alright that s a big component with a lot going on Let s break it down As usual we re importing out necessary dependancies as well as our useFetchGroceryItems custom hook We re taking in the token which we will pass in from the Dashboard then we have this Now if you haven t taken the opportunity to head over to the React Query docs now would be another great time to do so What we have here is a destructured Array which we are pulling from the useFetchGroceryItems hook we built earlier jsxconst data groceryItems error isLoading useFetchGroceryItems token This allows us to check and handle our Loading status check and handle any errors and finally display the data Awesome Hit save and we ll head to the browser to add a couple of items to our list That looks alright but did you notice how long it took to update Isn t it called “Real Time Database What gives Well remember how we talked about how React Query manages caching and state Well now it s time to learn about another awesome feature Optimistic updates Optimistic updates aren t a new idea nor are they overly complex Essentially you push the data to your state while pushing the data to the server you synchronize with But what if your mutation fails or the user cancels the mutation mid process That s where React Query comes in handy Let s head back into our useAddGroceryItem js file jsx useAddGroceryItem jsimport useMutation from react query import addGroceryItem from api addGroceryItem export const useAddGroceryItem token queryClient gt const mutation useMutation mutationFn groceryItem gt addGroceryItem groceryItem token onMutate async groceryItem gt await queryClient cancelQueries queryKey groceryItems const prevItems queryClient getQueryData groceryItems queryClient setQueryData groceryItems old gt old old groceryItem id groceryItem return prevItems onError error groceryItem context gt console log An error occurred while adding the grocery item groceryItem Error error queryClient setQueryData groceryItems context prevItems return context prevItems onSuccess data context gt console log Grocery item added successfully data onSettled gt queryClient invalidateQueries queryKey groceryItems return mutation Remember the side effects we talked about Now we re showing off their real power Let s break down what we re doing here First we define the mutationFn what we actually want the function to DO In this case we re calling our addGroceryItem function and passing in the new groceryItem with our token Next we re calling the “onMutate side effect This is where we are performing our optimistic updates When the mutation is called we cancel any current occurrences of the groceryItems query we then get a snapshot of the current state and push our new item into that state We then return the previous items passing them into our error handler Here if we run into an issue we are able to quickly log the problem and roll back to our previous state We could also display an error message or redirect the user as is necessary Then when the Error and Success handling have completed we invalidate the groceryItems query and refetch from the back end Now one thing you ll notice here we ve added in the queryClient variable That needs to be retrieved and passed in from the dashboard jsx Dashboard jsximport React useContext from react import Box Typography from mui material import GroceryItemInputForm from components GroceryItemInputForm import GroceryList from components GroceryList import getAuth from firebase auth import useQueryClient from react query const Dashboard gt const currentUser getAuth const queryClient useQueryClient const token currentUser accessToken return currentUser Welcome to the Dashboard currentUser Logged in as currentUser email export default Dashboard Here we ve imported the useQueryClient hook from React Query which we use to call our contextual Query Client Remember since we re calling this within a single context the cache is shared and the mutations and queries are all interconnected Take another look at useFetchGroceryItems jsximport useQuery from react query import fetchGroceryItems from api fetchGroceryItems export const useFetchGroceryItems token gt return useQuery groceryItems gt fetchGroceryItems token The groceryItems key that we re using is unique to this hook and it can be used to invalidate the items in this specific call simply by using the string key and the QueryClient Now because we re invalidated the query we re going to run into some scenarios where groceryItems null and we didn t set up our GroceryList to handle that scenario jsx GroceryList jsxconst GroceryList token gt const data groceryItems error isLoading useFetchGroceryItems token if isLoading groceryItems Loading handler if error Error handling if groceryItems return Grocery List component export default GroceryList There you have it We ve added some elegant handling for adding items and automatically refreshing our list on update Wrapping UpBy no means are we “done here But we re off to a great start In this walkthrough together we hooked up our Firebase Auth and Realtime Database we created our Express server with our back end API routes we developed our React Front End to display and add our grocery items Also it runs on the Node Engine Yay FERN Our next steps are going to include Adding a check mark to mark as completedEdit itemsRemove itemsRemoving completed items after a set period of timeBuilding the Front end for ProductionContainerizingHosting I really hope you enjoyed this walk through it s my first time ever putting one together Please let me know your thoughts and if you have any questions or comments You can find the completed github repo here |
2023-04-18 19:05:32 |
海外TECH |
DEV Community |
Top 7 Featured DEV Posts from the Past Week |
https://dev.to/devteam/top-7-featured-dev-posts-from-the-past-week-4o7a
|
Top Featured DEV Posts from the Past WeekEvery Tuesday we round up the previous week s top posts based on traffic engagement and a hint of editorial curation The typical week starts on Monday and ends on Sunday but don t worry we take into account posts that are published later in the week Document or Die The Importance of Writing Things Down in TechDocumentation can often seem like a secondary task but skipping it can really come back to bite you So if you want to avoid getting caught up in a huge time sink follow these tips from tyagi data wizard Document or Die The Importance of Writing Things Down in Tech Ujjwal Tyagi・Apr ・ min read beginners devjournal development documentation How To Use MVVM in React Using Hooks and TypeScriptIn this article perssondennis takes a look at how a React application can be designed to follow the MVVM architectural design pattern to create a React application that is both scalable and maintainable How To Use MVVM in React Using Hooks and TypeScript Dennis Persson・Apr ・ min read react architecture webdev javascript Becoming an Astro Maintainer eliancodes shares their experience becoming an Astro maintainer along with all of the exciting plans for what s in store for the future Elian s open source experience is definitely one you could learn from so read on to find out more Becoming an Astro maintainer Elian Van Cutsem・Apr ・ min read astro opensource javascript webdev Costly CSS Properties and How to Optimize ThemSome CSS properties are more costly than others in terms of performance When used improperly they can slow down your webpage and make it less responsive for your users In this article leduc explores some of the most costly CSS properties and how to optimize them Costly CSS Properties and How to Optimize Them Duc Le・Apr ・ min read webdev css html frontend When to use currying in JavaScriptThis post from slimtim is about the concept of currying from functional programming and when you should use it in JavaScript It might not be useful if you aren t going to implement functional programming but it might get you curious about how it works When to use currying in JavaScript SlimTim・Apr ・ min read webdev javascript programming beginners The importance of rel canonical for content writers nfrankel touches on the problem of content duplication and how simply writing the best article isn t enough You need to know how to spread your content across the web in a way that directs it back towards the source Follow these tips to make sure your original content is given preference in search engines The importance of rel canonical for content writers Nicolas Frankel・Apr ・ min read seo content contentwriting C C Sharp CRUD Rest API using NET ASP NET Entity Framework Postgres Docker and Docker ComposeLet s create a CRUD Rest API in C with francescoxx using NET ASP NET Entity Framework Postgres Docker and Docker Compose You can follow along using the tutorial video available or by heading to the GitHub repo to check out the code for yourself C C Sharp CRUD Rest API using NET ASP NET Entity Framework Postgres Docker and Docker Compose Francesco Ciulla・Apr ・ min read dotnet webdev beginners docker That s it for our weekly Top for this Tuesday Keep an eye on dev to this week for daily content and discussions and be sure to keep an eye on this series in the future You might just be in it |
2023-04-18 19:02:49 |
Apple |
AppleInsider - Frontpage News |
New Beats Studio Buds+ release may be imminent |
https://appleinsider.com/articles/23/04/18/new-beats-studio-buds-release-may-be-imminent?utm_medium=rss
|
New Beats Studio Buds release may be imminentEvidence for the rumored Beats Studio Buds is growing as a Federal Communications Commission filing reveals the new model with audio sharing and other features is coming soon Beats Studio BudsIn the release candidate version of iOS developer Aaron found references to new AirPods models They mentioned possible new versions of AirPods and Beats headphones Read more |
2023-04-18 19:47:17 |
Apple |
AppleInsider - Frontpage News |
16-inch MacBook Pro vs LG Gram 17 - compared |
https://appleinsider.com/inside/16-inch-macbook-pro/vs/16-inch-macbook-pro-vs-lg-gram-17---compared?utm_medium=rss
|
inch MacBook Pro vs LG Gram comparedLG has updated its Gram series of laptops with the new LG Gram a lightweight notebook with a large screen Here s how it compares with the newest inch MacBook Pro models with an M Pro or M Max chip MacBook Pro vs LG GramThe Gram started shipping on February though LG announced the new computer in January at CES It includes the latest technologies such as an Intel Core i processor and an Nvidia GPU Read more |
2023-04-18 19:03:21 |
Apple |
AppleInsider - Frontpage News |
Drop Ultrasonic keyboard review: premium typing but difficult customization |
https://appleinsider.com/articles/23/04/17/drop-ctrl-mechanical-keyboard-review-premium-typing-but-difficult-customization?utm_medium=rss
|
Drop Ultrasonic keyboard review premium typing but difficult customizationThe Drop Signature Series Ultrasonic Keyboard is a good keyboard for entering the world of mechanical keyboards although the price is high compared to other mechanical keyboards Drop Ultrasonic keyboardIt s a superb mechanical keyboard with a premium design and high end features Drop designed it to provide an outstanding typing experience for gamers programmers and typists Read more |
2023-04-18 19:15:59 |
海外TECH |
Engadget |
Netflix will shut down its DVD rental business in September |
https://www.engadget.com/netflix-will-shut-down-its-dvd-rental-business-in-september-195213827.html?src=rss
|
Netflix will shut down its DVD rental business in SeptemberAfter years Netflix s original business is shutting down The company has revealed that it will quot wind down quot DVD rentals that is DVD com with its last movie discs mailing on September th Simply put the shrinking demand for physical rentals is making it quot increasingly difficult quot to offer the service the company wants Netflix shipped its first disc Beetlejuice if you re curious in It has since mailed over billion movies in its signature red envelopes nearly all of them before to more than million customers You likely know the story after that The company began streaming on demand video in and that business grew quickly enough that it became Netflix s dominant offering After a premature attempt to spin off the mailed rentals as Qwikster in Netflix moved them to DVD com in By that point the company was well into producing original streaming shows Developing This article originally appeared on Engadget at |
2023-04-18 19:52:13 |
海外TECH |
Engadget |
Meta's Horizon Worlds is opening to young teens in the US and Canada |
https://www.engadget.com/metas-horizon-worlds-is-opening-to-young-teens-in-the-us-and-canada-194600914.html?src=rss
|
Meta x s Horizon Worlds is opening to young teens in the US and CanadaMonths later than rumored Meta s Horizon Worlds is opening its doors to younger teens The company is making its metaverse space accessible to teens aged to in the US and Canada in the weeks ahead Unsurprisingly the company is promising quot robust quot safety measures and parental controls ーit wants to be sure the experience is age appropriate and the gradual rollout will help it gauge how well those protections are working Teens Horizon Worlds profiles will be private by default and won t automatically show locations or active statuses They won t see unfamiliar adults in their quot people you might know quot lists Age ratings prevent teens from creating or using mature content and a quot voice mode quot garbles the voices of anyone that isn t following back These younger users will also get safety tips while they re in VR nbsp Parents can use the Meta Quest app or Family Center now available for Horizon Worlds to control features like personal boundaries They can also allow or block apps track usage and see who s following who All users can cast their VR view to an external screen so a parent in the room can see what s happening The strategy closely reflects Meta s approach to teen safety on Facebook and Instagram That won t necessarily please everyone Senators have urged Meta to keep teens off Horizon Worlds over concerns the company s safeguards may be inadequate They ve noted that Meta s own research revealed harm to some teens and that other virtual spaces like VRChat are prone to predatory and toxic behavior There s plenty of pressure on Meta to expand however The social media giant has struggled to pivot to the metaverse and continues to lose billions investing in the Reality Labs unit behind Horizon Worlds and Quest headsets A wider teen audience could boost Horizon s audience and spur the market for VR hardware This article originally appeared on Engadget at |
2023-04-18 19:46:00 |
海外TECH |
Engadget |
Latest Apple headset rumors say it’ll include VR workouts and sports |
https://www.engadget.com/latest-apple-headset-rumors-say-itll-include-vr-workouts-and-sports-192316389.html?src=rss
|
Latest Apple headset rumors say it ll include VR workouts and sportsApple is reportedly readying a wide array of apps and services for its upcoming mixed reality headset according toBloomberg s Mark Gurman The company appears to be moving forward with plans to announce its first VR AR headset at its Worldwide Developers Conference in June The Apple mixed reality headset rumored to be named “Reality One or “Reality Pro can allegedly switch between virtual and augmented reality It will focus heavily on gaming fitness sports and collaboration tools Customers who buy the device can use “millions of existing apps in the headset s D interface “with slight modifications from developers Additionally Apple has reportedly been working with “a small number of developers for months to optimize apps for the new product Announcing the device months before its launch should also give other developers time to create new apps or adapt existing ones for its futuristic interface Although many of the product s details have leaked before a new morsel in this report is its ability to run Apple Fitness workouts in VR Imagine a virtual workout where you feel like you re in the same space as the instructor In addition it will allegedly support immersive sports viewing leveraging the company s streaming rights for Major League Soccer and Major League Baseball as well as its purchase of VR sports startup NextVR Likewise the Apple TV app will let you watch videos in virtual environments like a desert or the sky The report says the headset will have a productivity focus similar to the Meta Quest Pro “The platform will support its Pages word processing Numbers spreadsheet and Keynote slide deck apps as well as iMovie and GarageBand for video and music production writes Gurman It would also prioritize communication and remote collaboration letting users see full body D avatars of people they re talking with in FaceTime calls Gaming will also be a primary focus However that wasn t always the case as today s report says that Apple previously wasn t putting as much attention into that space Gurman also reiterates earlier reporting about the headset including a Digital Crown like the one on the Apple Watch and AirPods Max headphones that lets you switch between VR fully immersive no real world view and AR using cameras to combine your real environment and virtual elements It would support running multiple apps simultaneously “floating within the mixed reality interface It could also remember where you were in your physical environment leaving virtual elements in the same spot you left them We saw that feature as far back as the first HoloLens developer kit in The headset would also let you control it with eye gestures that determine where you re looking and hand gestures like finger pinches to select items and navigate menus In addition it will have an in air virtual keyboard and support physical keyboards for a more tactile typing experience Its home screen could appear similar to the iPad s with Apple s familiar Control Center for toggling things like WiFi Bluetooth and volume Finally it will support Siri voice control and use eye scans for security acting as the device s equivalent to Face ID and Touch ID Although the product will supply a robust feature set that will elicit curiosity other companies have tried similar things but have yet to succeed For example although the cheaper Meta Quest VR headsets have done reasonably well as gaming devices the more expensive Meta Quest Pro ーwith a similar mixed reality focus and productivity apps ーhas been a tougher sell to consumers And Apple s version will reportedly cost around three times as much ーa staggering On the other hand Apple s history requires us to keep a somewhat open mind There were MP players before the iPod smartphones before the iPhone and smartwatches before the Apple Watch Those competing devices all had similar features but failed to capture the public s imagination in the same way as Apple s stylish and user friendly variants Even if the product targets a niche audience it could serve a purpose as a consumer facing transition product pointing toward an eventual pair of AR glasses that passes for a regular pair of prescription frames Seen by many in the industry as the holy grail of mixed reality such a device could be worn all day out in the world while the upcoming mixed reality headset expected in June would not This article originally appeared on Engadget at |
2023-04-18 19:23:16 |
海外TECH |
Engadget |
Designing for a better future: Framlab’s vision for urban architecture |
https://www.engadget.com/framlab-design-research-lab-sustainable-architecture-video-191542871.html?src=rss
|
Designing for a better future Framlab s vision for urban architectureWhen it comes to sustainability cities represent both the problem and the solution Sprawling slabs of concrete and asphalt create heat islands resulting in significantly higher temperatures than non urbanized areas while city populations are only growing as the planet becomes more populous Already more than percent of humans live in urban areas Framlab is a research and design studio based in Bergen Norway and Brooklyn New York and architects there are focused on rethinking the way we build city spaces Framlab founder Andreas Tjeldflaat believes there s a need to overhaul conventional urban planning with an eye on inclusion adaptability and regeneration His concepts address micro and macro level societal issues from feelings of personal isolation to the consequences of human driven climate change They also end up looking extremely sleek Tjeldflaat outlined three conceptual projects for us each one addressing a different problem in growing cities Open House is a building designed to encourage interpersonal interaction through the use of soft edges and shared spaces while Oversky places floating cloud like buildings above the city streets Glasir takes advantage of leftover urban spaces like empty lots and streetside landscaping by establishing large glass treehouses with community gardens inside their branches Watch the video for the below for the full story This article originally appeared on Engadget at |
2023-04-18 19:15:42 |
海外TECH |
Engadget |
Horizon Forbidden West's new accessibility features address the fear of deep water |
https://www.engadget.com/horizon-forbidden-wests-new-accessibility-features-address-the-fear-of-deep-water-190444188.html?src=rss
|
Horizon Forbidden West x s new accessibility features address the fear of deep waterHorizon Forbidden West is a fantastic game Along with upgraded gameplay and visuals and an even wilder story it builds on the vast open world of Horizon Zero Dawn by introducing fresh environments to explore including flooded areas and the open ocean nbsp However those who have a fear of deep bodies of water thalassophobia may not have found it easy to play the game which requires players to explore underwater as part of the main story Guerrilla is finally addressing that and other accessibility issues in the latest patch The update which arrives alongside the Burning Shores expansion adds a thalassophobia mode to Horizon Forbidden West The studio wrote in an FAQ that this quot aims to ease thalassophobia symptoms by improving underwater ambient visibility and allowing you to breathe indefinitely regardless of story progression quot We hope you will all enjoy your new adventure with Aloy If you have questions about Horizon Forbidden West Burning Shores please check out some of our helpful resources below Frequently Asked Questions Game Support pic twitter com XsvxjZYvwーGuerrilla Guerrilla April Other updates include additional color blindness settings and the option to make waypoints and quest icons larger There s now a way to reorientate the camera in Focus mode to point it towards the current objective along with an auto camera function that follows Aloy based on how you move the left thumbstick In other words you won t need to use the right stick to move the camera In addition there are larger subtitles and the ability to darken the edges of the screen to boost the contrast The update rolls in one more very welcome quality of life feature in the form of automatic pickups So Aloy can grab items without you having to press or hold a button every single time Sony has placed a greater focus on accessibility in its first party games in recent years The likes of The Last of Us Part II Ratchet and Clank Rift Apart and God of War Ragnarok have extensive accessibility options The company hasn t quite perfected accessibility ーa review of The Last of Us Part I on PC criticized that version for not offering full control remapping But as this update to Horizon Forbidden West over a year after the game s debut shows the company is willing to keep improving its games accessibility over time This article originally appeared on Engadget at |
2023-04-18 19:04:44 |
海外科学 |
NYT > Science |
FDA Authorizes Another Covid Booster Shot for People Over 65 |
https://www.nytimes.com/2023/04/18/health/covid-booster-shots-seniors.html
|
FDA Authorizes Another Covid Booster Shot for People Over Seniors and people with compromised immune systems may get a second bivalent booster if at least four months have passed since their last one |
2023-04-18 19:51:12 |
医療系 |
医療介護 CBnews |
これからの広報を考える(その1)-「病院広報アワード」受賞への道(2) |
https://www.cbnews.jp/news/entry/20230418174003
|
取り組み |
2023-04-19 05:00:00 |
ニュース |
BBC News - Home |
SNP treasurer Colin Beattie released without charge |
https://www.bbc.co.uk/news/uk-scotland-65318516?at_medium=RSS&at_campaign=KARANGA
|
finances |
2023-04-18 19:35:04 |
ニュース |
BBC News - Home |
Ralph Yarl: Andrew Lester, accused of shooting black teen, is in custody |
https://www.bbc.co.uk/news/world-us-canada-65316073?at_medium=RSS&at_campaign=KARANGA
|
doorbell |
2023-04-18 19:30:42 |
ニュース |
BBC News - Home |
Sudan fighting continues despite ceasefire |
https://www.bbc.co.uk/news/world-africa-65317693?at_medium=RSS&at_campaign=KARANGA
|
respite |
2023-04-18 19:17:16 |
ニュース |
BBC News - Home |
Secret Service nabs toddler who squeezed through White House fence |
https://www.bbc.co.uk/news/world-us-canada-65282085?at_medium=RSS&at_campaign=KARANGA
|
fencethe |
2023-04-18 19:11:12 |
ニュース |
BBC News - Home |
Six injured and school locked down over dog attack |
https://www.bbc.co.uk/news/uk-england-birmingham-65315850?at_medium=RSS&at_campaign=KARANGA
|
attackthe |
2023-04-18 19:09:32 |
ニュース |
BBC News - Home |
Bannau Brycheiniog: Views on national park's name change |
https://www.bbc.co.uk/news/uk-wales-65299312?at_medium=RSS&at_campaign=KARANGA
|
english |
2023-04-18 19:27:48 |
ビジネス |
ダイヤモンド・オンライン - 新着記事 |
異才を殺す上司、生かす上司の差とは…「大谷翔平級」な部下の扱いどうする? - 「40代で戦力外」にならない!新・仕事の鉄則 |
https://diamond.jp/articles/-/321047
|
大谷翔平 |
2023-04-19 04:55:00 |
ビジネス |
ダイヤモンド・オンライン - 新着記事 |
PwCコンサルが「アクセンチュアと真逆」の戦略を採る理由、トップが明かす欲しい人材像【動画】 - コンサル採用解剖図鑑 |
https://diamond.jp/articles/-/321109
|
PwCコンサルが「アクセンチュアと真逆」の戦略を採る理由、トップが明かす欲しい人材像【動画】コンサル採用解剖図鑑PwCコンサルティングのトップが明かす、「アクセンチュアとは真逆」の独自戦略とは特集『コンサル採用解剖図鑑』PwCコンサルティング編の第回は、同社がワンストップを目指さない理由と、勝ち残りのための組織変革に迫る。 |
2023-04-19 04:50:00 |
ビジネス |
ダイヤモンド・オンライン - 新着記事 |
日銀政策以外にも「円高」促す3つの理由、120円割れのリスクも - 政策・マーケットラボ |
https://diamond.jp/articles/-/321512
|
不確実性 |
2023-04-19 04:45:00 |
ビジネス |
ダイヤモンド・オンライン - 新着記事 |
緩和維持の植田日銀、2%物価目標「未達成でもやれること」はある - 経済分析の哲人が斬る!市場トピックの深層 |
https://diamond.jp/articles/-/321510
|
国債市場 |
2023-04-19 04:40:00 |
ビジネス |
ダイヤモンド・オンライン - 新着記事 |
【三鷹市ベスト5】小学校区「教育環境力」ランキング!【偏差値チャート最新版】 - 東京・小学校区「教育環境力」ランキング2022 |
https://diamond.jp/articles/-/321511
|
【三鷹市ベスト】小学校区「教育環境力」ランキング【偏差値チャート最新版】東京・小学校区「教育環境力」ランキング子どもにとってよりよい教育環境を目指し、入学前に引っ越して小学校区を選ぶ時代になった。 |
2023-04-19 04:35:00 |
ビジネス |
ダイヤモンド・オンライン - 新着記事 |
バフェット氏の投資術は「今も進化中」かもしれない - 山崎元のマルチスコープ |
https://diamond.jp/articles/-/321508
|
進化 |
2023-04-19 04:30:00 |
ビジネス |
ダイヤモンド・オンライン - 新着記事 |
KDDI高橋誠社長が明かす「稲盛和夫さんと過ごした新人時代」の幸運 - News&Analysis |
https://diamond.jp/articles/-/321041
|
KDDI高橋誠社長が明かす「稲盛和夫さんと過ごした新人時代」の幸運NewsampampAnalysis稀代の経営者、稲盛和夫氏の人生哲学を信奉する人も多い。 |
2023-04-19 04:25:00 |
ビジネス |
ダイヤモンド・オンライン - 新着記事 |
日本には「世襲政治家」が多すぎる、ビジネス界からの転身が少ない根本理由 - 上久保誠人のクリティカル・アナリティクス |
https://diamond.jp/articles/-/321431
|
日本には「世襲政治家」が多すぎる、ビジネス界からの転身が少ない根本理由上久保誠人のクリティカル・アナリティクス昨今は「世襲政治家」への批判が再燃している。 |
2023-04-19 04:20:00 |
ビジネス |
ダイヤモンド・オンライン - 新着記事 |
スーパー「オーケー」がピザ焼き色判定にAI導入!直面した思わぬ落とし穴とは - 酒井真弓のDX最前線 |
https://diamond.jp/articles/-/321507
|
|
2023-04-19 04:15:00 |
ビジネス |
ダイヤモンド・オンライン - 新着記事 |
「親の介護に悩む社員」を救う企業になれる!超簡単な社員向け老親リスク対策 - News&Analysis |
https://diamond.jp/articles/-/321168
|
「親の介護に悩む社員」を救う企業になれる超簡単な社員向け老親リスク対策NewsampampAnalysis長寿命化、超高齢化が進む日本では、代以上のビジネスパーソンの多くが「親の介護問題」に直面することになります。 |
2023-04-19 04:10:00 |
ビジネス |
ダイヤモンド・オンライン - 新着記事 |
伊藤穰一氏が就活生に直言、「日本の強みを生かしweb3の世界潮流に乗る!」 - 親と子の「就活最前線」 |
https://diamond.jp/articles/-/315854
|
伊藤穰一 |
2023-04-19 04:05:00 |
ビジネス |
東洋経済オンライン |
「さっさと宿題が終わる子」に激変する6つのコツ カバンの中身は帰宅後すぐに全部出す | 子どもを本当に幸せにする「親の力」 | 東洋経済オンライン |
https://toyokeizai.net/articles/-/666258?utm_source=rss&utm_medium=http&utm_campaign=link_back
|
東洋経済オンライン |
2023-04-19 04:50:00 |
ビジネス |
東洋経済オンライン |
どんなルートがある?東南アジア「国際列車」事情 中国ラオス直結の一方、ほかの国境は縮小傾向 | 海外 | 東洋経済オンライン |
https://toyokeizai.net/articles/-/667130?utm_source=rss&utm_medium=http&utm_campaign=link_back
|
国際列車 |
2023-04-19 04:30:00 |
コメント
コメントを投稿